自自然卷 2016-12-08 13:28 采纳率: 35.7%
浏览 1344
已采纳

Java openConnection问题

URL url = new URL("http://www.sina.com.cn");
HttpURLConnection urlConnection = (HttpURLConnection) (url.openConnection());

上面第二句中url.openConnection调用的不是URLStreamHandler里的抽象函数openConnection吗
我找不到有哪个子类实现了openConnection,想问哪个子类实现了openConnection?
谢谢!

  • 写回答

2条回答 默认 最新

  • Readiay 2016-12-09 02:05
    关注

    我来给你找一下,首先你点开url.openConnection();

         public URLConnection openConnection() throws java.io.IOException {
            return handler.openConnection(this);
        }
    

    你发现这里是handler调用的,但是这个handler是怎么赋值的呢?于是你就需要找哪里初始化了这个handler

    在java里面,初始化一个对象,要么静态代码块,要么就是构造器里面,于是现在我们点进去URL那个构造器里面

     public URL(URL context, String spec, URLStreamHandler handler)
            throws MalformedURLException
    

    经过层层点击,最终调用的是方法签名是如上的这个类,于是你就看那个handler,哪里出现了,哪里初始化了

                 // Get the protocol handler if not specified or the protocol
                // of the context could not be used
                if (handler == null &&
                    (handler = getURLStreamHandler(protocol)) == null) {
                    throw new MalformedURLException("unknown protocol: "+protocol);
                }
    
                this.handler = handler;
    

    你就随便看几眼,你就能看到这里是赋值了,然后你还发现上面if条件里面有个判断,就是如果handler == null,
    就调用了getURLStreamHandler()这个方法,点进去

    图片说明

    你会发现这里有一个工厂,如果这个协议没有得到handler就从工场里面获取handler。点进去看看

     private static class Factory implements URLStreamHandlerFactory {
            private static String PREFIX = "sun.net.www.protocol";
    
            public URLStreamHandler createURLStreamHandler(String paramString) {
                String str = PREFIX + "." + paramString + ".Handler";
                try {
                    Class localClass = Class.forName(str);
                    return ((URLStreamHandler) localClass.newInstance());
                } catch (ClassNotFoundException localClassNotFoundException) {
                    localClassNotFoundException.printStackTrace();
                } catch (InstantiationException localInstantiationException) {
                    localInstantiationException.printStackTrace();
                } catch (IllegalAccessException localIllegalAccessException) {
                    localIllegalAccessException.printStackTrace();
                }
                throw new InternalError("could not load " + paramString + "system protocol handler");
            }
        }
    

    这里你就会发现,他使用字符串拼凑的方式,产生一个类的路径,于是你想找的那个类就是在

    sun.net.www.protocol.http.Handler 就是这个类

    这里多次出现了protocol, 这个是什么呢?

    比如说:http://www.baidu.com ftp://192.168.133.100
    https://www.baidu.com

    这个URL长的都蛮像的,其实这个protocol、就是前面的http,https,ftp等
    表示使用什么通信协议。

    所以你就会发现,如果你使用的是ftp开头的,那么这个handler就是

    sun.net.www.protocol.ftp.Handler

    如果你觉得答得不错,就采纳吧

    本回答被题主选为最佳回答 , 对您是否有帮助呢?
    评论
查看更多回答(1条)

报告相同问题?

悬赏问题

  • ¥15 fluent的在模拟压强时使用希望得到一些建议
  • ¥15 STM32驱动继电器
  • ¥15 Windows server update services
  • ¥15 关于#c语言#的问题:我现在在做一个墨水屏设计,2.9英寸的小屏怎么换4.2英寸大屏
  • ¥15 模糊pid与pid仿真结果几乎一样
  • ¥15 java的GUI的运用
  • ¥15 Web.config连不上数据库
  • ¥15 我想付费需要AKM公司DSP开发资料及相关开发。
  • ¥15 怎么配置广告联盟瀑布流
  • ¥15 Rstudio 保存代码闪退