若天明 发表于 2015-1-18 11:14:22

JAVA教程之Java 实际与理论: 伪typedef反形式

还是要自己一点一点写代码,然后编译,改错再编译好那。还有最重要的是.net的编译环境非常好,你甚是不需要了解太多工具,对于简单的系统,你可以之了解一些语法就哦了。  将泛型增加到Java言语中增添了范例体系的庞大性,进步了很多变量和办法声明的冗杂水平。由于没有供应“typedef”工具来界说范例的冗长称号,以是有些开辟职员转而把扩大看成“穷汉的typedef”,了局收到了优秀的效果。

  关于Java5.0中新增的泛型工具,一个罕见的埋怨就是,它使代码变得太冗杂。本来用一行就够的变量声明不再存在了,与声明参数化范例有关的反复十分厌恶,出格是还没有优秀地撑持主动补足的IDE。比方,假如想声明一个Map,它的键是Socket,值是Future<String>,那末老办法就是:

MapsocketOwner=newHashMap();
  比新办法松散很多:

Map<Socket,Future<String>>socketOwner=newHashMap<Socket,Future<String>>();
  固然,新办法内置了更多范例信息,削减了编程毛病,进步了程序的可读性,可是的确带来了更多声明变量和办法署名方面的后期事情。范例参数在声明和初始化中的反复看起来特别没有需要;Socket和Future<String>必要输出两次,这迫使我们背犯了“DRY”准绳(不要反复本人)。

  分解相似于typedef的工具

  增加泛型给范例体系增添了一些庞大性。在Java5.0之前,“type”和“class”几近是同义的,而参数化范例,出格是那些绑定的通配范例,使子范例和子类的观点有了明显区分。范例ArrayList<?>、ArrayList<?extendsNumber>和ArrayList<Integer>是分歧的范例,固然它们是由统一个类ArrayList完成的。这些范例组成了一个条理布局;ArrayList<?>是ArrayList<?extendsNumber>的超范例,而ArrayList<?extendsNumber>是ArrayList<Integer>的超范例。

  关于本来的复杂范例体系,像C的typedef如许的特征没成心义。可是关于更庞大的范例体系,typedef工具大概会供应一些优点。不知是好仍是坏,总之在泛型到场的时分,typedef没有到场Java言语。

  有些人用作“穷汉的typedef”的一个(坏的)做法是一个小小的扩大:创立一个类,扩大泛型范例,可是不增加功效,比方SocketUserMap范例,如清单1所示:

  清单1.伪typedef反形式――不要这么做

publicclassSocketUserMapextendsHashMap<Socket<Future<String>>{}SocketUserMapsocketOwner=newSocketUserMap();
  我将这个技能称为伪typedef反形式,它完成了将socketOwner界说简化为一行的这一(有成绩的)方针,可是有些反作用,终极成为重用和保护的停滞。(关于有明白的机关函数而不是无参机关函数的类来讲,派生类也必要声明每一个机关函数,由于机关函数没有被承继。)

  伪范例的成绩

  在C中,用typedef界说一个新范例更像是宏,而不是范例声明。界说等价范例的typedef,能够与原始范例自在地交换。清单2显现了一个界说回调函数的示例,个中在署名中利用了一个typedef,可是挪用者供应给回调的是一个等价范例,而编译器和运转时都能够承受它:

  清单2.C言语的typedef示例
//Defineatypecalled"callback"thatisafunctionpointertypedefvoid(*Callback)(int);voiddoSomething(Callbackcallback){}//ThisfunctionconformstothetypedefinedbyCallbackvoidcallbackFunction(intarg){}//SoacallercanpasstheaddressofcallbackFunctiontodoSomethingvoiduseCallback(){doSomething(&callbackFunction);}
  扩大不是范例界说

  用Java言语编写的试图利用伪typedef的等价程序就会呈现贫苦。清单3的StringList和UserList范例都扩大了一个大众超类,可是它们不是等价的范例。这意味着任何想挪用lookupAll的代码都必需传送一个StringList,而不克不及是List<String>或UserList。

  清单3.伪范例怎样把客户限制在只能利用伪范例
classStringListextendsArrayList<String>{}classUserListextendsArrayList<String>{}...classSomeClass{publicvoidvalidateUsers(UserListusers){...}publicUserListlookupAll(StringListnames){...}}
  这个限定要比初看上往严厉很多。在小程序中,大概不会有太年夜差别,可是当程序变年夜的时分,利用伪范例的需求就会不休地形成成绩。假如变量范例是StringList,就不克不及给它分派一般的List<String>,由于List<String>是StringList的超范例,以是不是StringList。就像不克不及把Object分派给范例为String的变量一样,也不克不及把List<String>分派给范例为StringList的变量(可是,能够反过去,比方,能够把StringList分派给范例为List<String>的变量,由于List<String>是StringList的超范例。)

  一样的情形也合用于办法的参数;假如一个办法参数是StringList范例,那末就不克不及把一般的List<String>传送给它。这意味着,假如不请求这个办法的每次利用都利用伪范例,那末基本不克不及用伪范例作为办法参数,而这在理论傍边就意味着在库API中基本就不克不及利用伪范例。并且年夜多半库API都源自原本没想成为库代码的那些代码,以是“这个代码只是给我本人的,没有其别人会用它”可不是个好托言(只需您的代码有一点儿用途,他人就有大概会利用它;假如您的代码臭得很,那您多是对的)。
<P>  伪范例会感染

  这类“病毒”性子是让C代码的重用有坚苦的要素之一。差未几每一个C包都有头文件,界说工具宏和范例,像int32、boolean、true、false,诸云云类。假如想在一个使用程序内利用几个包,而它们关于这些大众条目没有利用不异的界说,那末即便要编译一个只包括一切头文件的空程序,之前也要在“头文件天堂”成绩上花好长工夫。假如编写的C使用程序要利用很多来自分歧作者的分歧的包,那末几近一定要触及一些这类疾苦。另外一方面,关于Java使用程序来讲,在没有这类疾苦的情形下利用很多乃至更多的包,长短经常见的事。假如包要在它们的API中利用伪范例,那末我们大概就要从头履历早已留在疾苦回想中的成绩。

  作为示例,假定有两个分歧的包,每一个包都用伪范例反形式界说了StringList,如清单4所示,并且每一个包都界说了操纵StringList的工具办法。两个包都界说了一样的标识符,这一现实已是不便利的一个小泉源了;客户程序必需选择导进一个界说,而另外一个界说则要利用完整限制的称号。可是更年夜的成绩是如今这些包的客户没法创立既能传送给sortList又能传送给reverseList的对象,由于两个分歧的StringList范例是分歧的范例,相互互不兼容。客户如今必需在利用一个包仍是利用另外一个包之间举行选择,不然他们就必需做很多事情,在分歧范例的StringList之间举行转换。对包的作者来讲觉得便利的工具,成为在一切中央利用这个包的凸起停滞,除非在最受限的情况中。

  清单4.伪范例的利用怎样妨害重用
packagea;classStringListextendsArrayList<String>{}classListUtilities{publicstaticvoidsortList(StringListlist){}}packageb;classStringListextendsArrayList<String>{}classSomeOtherUtilityClass{publicstaticvoidreverseList(StringListlist){}}...classClient{publicvoidsomeMethod(){StringListlist=...;//CantdothisListUtilities.sortList(list);SomeOtherUtilityClass.reverseList(list);}}
  伪范例一般太详细

  伪范例反形式的进一步成绩是,它会损失利用接口界说变量范例和办法参数的优点。固然能够把StringList界说成扩大List<String>的接口,再界说一个详细范例StringArrayList来扩大ArrayList<String>并完成StringList,但多半伪typedef反形式的用户一般达不到这类程度,由于这项手艺的目标次要是为了简化和延长范例的称号。但了局是,API的用途削减了并变得更懦弱,由于它们利用ArrayList如许的详细范例,而不是List如许的笼统范例。

  更平安的技能

  一个更平安的削减声明泛型汇合所需打字量的技能是利用范例推导(typeinference)。编译器能够十分伶俐地利用程序中内嵌的范例信息来分派范例参数。假如界说了上面如许一个工具办法:

publicstatic<K,V>Map<K,V>newHashMap(){returnnewHashMap<K,V>();}
  那末能够平安地用它来制止录进两次参数:

Map<Socket,Future<String>>socketOwner=Util.newHashMap();
  这类办法之以是可以见效,在于编译器能够依据泛型办法newHashMap()被挪用的地位推导出K和V的值。

  停止语

  伪typedef反形式的念头很复杂――开辟职员想要一种办法能够界说更松散的范例标识符,出格是在泛型把范例标识符变得更冗杂的时分。成绩在于这个做法在利用它的代码和代码的客户之间构成了严密的耦合,从而妨害了重用。不喜好泛型范例标识符的冗杂是能够了解的,但这不是办理成绩的举措。

市场分额,java比asp高一点,因为C#是仿照java开发的,所以哦C#能做的java都能做到,但是java能做的,C#不一定都能做到。毕竟是抄袭吗。

兰色精灵 发表于 2015-1-18 19:39:10

你一定会高兴地说,哈哈,原来成为Java高手就这么简单啊!记得Tomjava也曾碰到过一个项目经理,号称Java很简单,只要三个月就可以学会。

莫相离 发表于 2015-1-31 14:43:42

如果要向java web方向发展也要吧看看《Java web从入门到精通》学完再到《Struts2.0入门到精通》这样你差不多就把代码给学完了。有兴趣可以看一些设计模块和框架的包等等。

第二个灵魂 发表于 2015-2-1 20:12:04

让你能够真正掌握接口或抽象类的应用,从而在原来的Java语言基础上跃进一步,更重要的是,设计模式反复向你强调一个宗旨:要让你的程序尽可能的可重用。

老尸 发表于 2015-2-7 14:51:49

J2SE开发桌面应用软件比起 VC,VB,DEPHI这些传统开发语言来说,优势好象并不明显。J2ME对于初学者来说,好象又有点深奥,而且一般开发者很难有开发环境。

活着的死人 发表于 2015-2-22 08:21:43

你就该学一学Servlet了。Servlet就是服务器端小程序,他负责生成发送给客户端的HTML文件。JSP在执行时,也是先转换成Servlet再运行的。虽说JSP理论上可以完全取代Servlet,这也是SUN推出JSP的本意,可是Servlet用来控制流程跳转还是挺方便的,也令程序更清晰。接下来你应该学习一下Javabean了,可能你早就看不管JSP在HTML中嵌Java代码的混乱方式了,这种方式跟ASP又有什么区别呢?

因胸联盟 发表于 2015-3-6 20:20:52

如果你学过HTML,那么事情要好办的多,如果没有,那你快去补一补HTML基础吧。其实JSP中的Java语法也不多,它更象一个脚本语言,有点象ASP。

海妖 发表于 2015-3-11 20:39:03

Jive的资料在很多网站上都有,大家可以找来研究一下。相信你读完代码后,会有脱胎换骨的感觉。遗憾的是Jive从2.5以后就不再无条件的开放源代码,同时有licence限制。不过幸好还有中国一流的Java程序员关注它,外国人不开源了,中国人就不能开源吗?这里向大家推荐一个汉化的Jive版本—J道。Jive(J道版)是由中国Java界大名 鼎鼎的banq在Jive 2.1版本基础上改编而成, 全中文,增加了一些实用功能,如贴图,用户头像和用户资料查询等,而且有一个开发团队在不断升级。你可以访问banq的网站

小女巫 发表于 2015-3-19 11:45:40

学Java必读的两个开源程序就是Jive和Pet Store.。 Jive是国外一个非常著名的BBS程序,完全开放源码。论坛的设计采用了很多先进的技术,如Cache、用户认证、Filter、XML等,而且论坛完全屏蔽了对数据库的访问,可以很轻易的在不同数据库中移植。论坛还有方便的安装和管理程序,这是我们平时编程时容易忽略的一部份(中国程序员一般只注重编程的技术含量,却完全不考虑用户的感受,这就是我们与国外软件的差距所在)。

只想知道 发表于 2015-3-27 22:08:33

一直感觉JAVA很大,很杂,找不到学习方向,前两天在网上找到了这篇文章,感觉不错,给没有方向的我指了一个方向,先不管对不对,做下来再说。
页: [1]
查看完整版本: JAVA教程之Java 实际与理论: 伪typedef反形式