Java 强引用, 软引用, 弱引用, 虚引用

Java 强引用, 软引用, 弱引用, 虚引用 强引用 StrongReference 强引用是使用最普遍的引用。如果一个对象具有强引用,那垃圾回收器绝不会回收它。当内存空间不足,Java虚拟机宁愿抛出OutOfMemoryError错误,使程序异常终止,也不会靠随意回收具有强引用的对象来解决内存不足的问题。 Object o=new Object(); // 强引用 如果不使用时,要通过如下方式来弱化引用,如下: o=null; // 帮助垃圾收集器回收此对象 显式地设置o为null,或超出对象的生命周期范围,则gc认为该对象不存在引用,这时就可以回收这个对象。具体什么时候收集这要取决于gc的算法。 在一个方法的内部有一个强引用,这个引用保存在栈中,而真正的引用内容 (Object) 保存在堆中。当这个方法运行完成后就会退出方法栈,则引用内容的引用不存在,这个Object会被回收。 但是如果这个o是全局的变量时,就需要在不用这个对象时赋值为null,因为强引用不会被垃圾回收。 强引用在实际中有非常重要的用处,举个ArrayList的实现源代码: private transient Object[] elementData; public void clear() { modCount++; // Let gc do its work for (int i = 0; i < size; i++) elementData[i] = null; size = 0; } 在ArrayList类中定义了一个私有的变量elementData数组,在调用方法清空数组时可以看到为每个数组内容赋值为null。不同于elementData=null,强引用仍然存在,避免在后续调用 add()等方法添加元素时进行重新的内存分配。使用如clear()方法中释放内存的方法对数组中存放的引用类型特别适用,这样就可以及时释放内存。 软引用 SoftReference 如果内存空间足够,垃圾回收器就不会回收它,如果内存空间不足了,就会回收这些对象的内存。只要垃圾回收器没有回收它,该对象就可以被程序使用。软引用可用来实现内存敏感的高速缓存。 它兼有了StrongReference和WeakReference的好处,既能停留在内存中,又能在内存不足时去处理。 String str=new String("abc"); // 强引用 SoftReference<String> softRef=new SoftReference<String>(str); // 软引用 虚引用 PhantomReference ...

Created 17176-11-17 · Updated 9096-10-09 · 1 min · 143 words · -

阻塞队列 BlockingQueue

阻塞队列 BlockingQueue 什么是阻塞队列 阻塞队列 (BlockingQueue) 是一个支持两个附加操作的队列。这两个附加的操作是: 在队列为空时,获取元素的线程会等待队列变为非空。当队列满时,存储元素的线程会等待队列可用。阻塞队列常用于生产者和消费者的场景,生产者是往队列里添加元素的线程,消费者是从队列里拿元素的线程。阻塞队列就是生产者存放元素的容器,而消费者也只从容器里拿元素。 方法\处理方式 抛出异常 返回特殊值 一直阻塞 超时退出 插入方法 add(e) offer(e) put(e) offer(e,time,unit) 移除方法 remove() poll() take() poll(time,unit) 检查方法 element() peek() 不可用 不可用 抛出异常: 是指当阻塞队列满时候,再往队列里插入元素,会抛出IllegalStateException(“Queue full”)异常。当队列为空时,从队列里获取元素时会抛出NoSuchElementException异常 。 返回特殊值: 插入方法会返回是否成功,成功则返回true。移除方法,则是从队列里拿出一个元素,如果没有则返回null 一直阻塞: 当阻塞队列满时,如果生产者线程往队列里put元素,队列会一直阻塞生产者线程,直到拿到数据,或者响应中断退出。当队列空时,消费者线程试图从队列里take元素,队列也会阻塞消费者线程,直到队列可用。 超时退出: 当阻塞队列满时,队列会阻塞生产者线程一段时间,如果超过一定的时间,生产者线程就会退出。 Java里的阻塞队列 JDK7 提供了 7 个阻塞队列 ArrayBlockingQueue : 一个由数组结构组成的有界阻塞队列。 LinkedBlockingQueue : 一个由链表结构组成的有界阻塞队列。 PriorityBlockingQueue : 一个支持优先级排序的无界阻塞队列。 DelayQueue: 一个使用优先级队列实现的无界阻塞队列。 SynchronousQueue: 一个不存储元素的阻塞队列。 LinkedTransferQueue: 一个由链表结构组成的无界阻塞队列。 LinkedBlockingDeque: 一个由链表结构组成的双向阻塞队列。 在JDK1.5新增的Concurrent包中,BlockingQueue很好的解决了多线程中,如何高效安全"传输"数据的问题。通过这些高效并且线程安全的队列类,为我们快速搭建高质量的多线程程序带来极大的便利。 认识BlockingQueue 阻塞队列,顾名思义,首先它是一个队列,通过一个共享的队列,可以使得数据由队列的一端输入,从另外一端输出; 常用的队列主要有以下两种: (当然通过不同的实现方式,还可以延伸出很多不同类型的队列,DelayQueue就是其中的一种) 先进先出 (FIFO) : 先插入的队列的元素也最先出队列,类似于排队的功能。从某种程度上来说这种队列也体现了一种公平性。 后进先出 (LIFO) : 后插入队列的元素最先出队列,这种队列优先处理最近发生的事件。 ...

Created 20206-12-20 · Updated 9096-10-09 · 3 min · 467 words · -

JavaEE Web 工程/项目 目录结构

JavaEE Web 工程/项目 目录结构 Maven 标准目录结构 好的目录结构可以使开发人员更容易理解项目,为以后的维护工作也打下良好的基础。Maven2根据业界公认的最佳目录结构,为开发者提供了缺省的标准目录模板。Maven2的标准目录结构如下: src/main/java Application/Library sources src/main/resources Application/Library resources src/main/webapp Web application sources src/test/java Test sources src/test/resources Test resources src/main/filters Resource filter files src/main/assembly Assembly descriptors src/main/config Configuration files src/main/scripts Application/Library scripts src/test/filters Test resource filter files src/site Site LICENSE.txt Project's license NOTICE.txt Notices and attributions required by libraries that the project depends on README.txt Project's readme 使用目录模板,可以使 pom.xml 更简洁。因为 Maven2 已经根据缺省目录,预定义了相关的动作,而无需人工的干预。以 resources 目录为例: ...

Created 1016-01-01 · Updated 9096-10-09 · 1 min · 195 words · -

Java 获取客户端真实 IP 地址的两种方法

Java获取客户端真实IP地址的两种方法 http://dpn525.iteye.com/blog/1132318 在JSP里,获取客户端的IP地址的方法是: request.getRemoteAddr () ,这种方法在大部分情况下都是有效的。但是在通过了Apache,Squid等反向代理软件就不能获取到客户端的真实IP地址了。 在JSP里,获取客户端的IP地址的方法是: request.getRemoteAddr () ,这种方法在大部分情况下都是有效的。但是在通过了Apache,Squid等反向代理软件就不能获取到客户端的真实IP地址了。 如果使用了反向代理软件,将http://192.168.1.110: 2046/ 的URL反向代理为 http://www.javapeixun.com.cn / 的URL时,用request.getRemoteAddr () 方法获取的IP地址是: 127.0.0.1或192.168.1.110,而并不是客户端的真实IP。 经过代理以后,由于在客户端和服务之间增加了中间层,因此服务器无法直接拿到客户端的IP,服务器端应用也无法直接通过转发请求的地址返回给客户端。但是在转发请求的HTTP头信息中,增加了X-FORWARDED-FOR信息。用以跟踪原有的客户端IP地址和原来客户端请求的服务器地址。当我们访问http://www.javapeixun.com.cn/index.jsp/ 时,其实并不是我们浏览器真正访问到了服务器上的index.jsp文件,而是先由代理服务器去访问http://192.168.1.110: 2046/index.jsp ,代理服务器再将访问到的结果返回给我们的浏览器,因为是代理服务器去访问index.jsp的,所以index.jsp中通过request.getRemoteAddr () 的方法获取的IP实际上是代理服务器的地址,并不是客户端的IP地址。 于是可得出获得客户端真实IP地址的方法一: public String getRemortIP(HttpServletRequest request) { if (request.getHeader("x-forwarded-for") == null) { return request.getRemoteAddr(); } return request.getHeader("x-forwarded-for"); } 可是当我访问http://www.5a520.cn /index.jsp/ 时,返回的IP地址始终是unknown,也并不是如上所示的127.0.0.1或192.168.1.110了,而我访问http://192.168.1.110: 2046/index.jsp 时,则能返回客户端的真实IP地址,写了个方法去验证。原因出在了Squid上。squid.conf 的配制文件forwarded_for 项默认是为on,如果 forwarded_for 设成了 off 则: X-Forwarded-For: unknown 于是可得出获得客户端真实IP地址的方法二: public String getIpAddr(HttpServletRequest request) { String ip = request.getHeader("x-forwarded-for"); if(ip == null || ip.length() == 0 || "unknown".equalsIgnoreCase(ip)) { ip = request.getHeader("Proxy-Client-IP"); } if(ip == null || ip.length() == 0 || "unknown".equalsIgnoreCase(ip)) { ip = request.getHeader("WL-Proxy-Client-IP"); } if(ip == null || ip.length() == 0 || "unknown".equalsIgnoreCase(ip)) { ip = request.getRemoteAddr(); } return ip; } 可是,如果通过了多级反向代理的话,X-Forwarded-For的值并不止一个,而是一串IP值,究竟哪个才是真正的用户端的真实IP呢? ...

Created 13136-03-13 · Updated 9096-10-09 · 2 min · 340 words · -

Java JSON 类库: Json-lib, Gson, Jackson, FastJson

4款json的java类库, FastJson JSON(JavaScript Object Notation) 是一种轻量级的数据交换格式。 易于人阅读和编写。同时也易于机器解析和生成。 它基于JavaScript Programming Language, Standard ECMA-262 3rd Edition - December 1999的一个子集。 JSON采用完全独立于语言的文本格式,这些特性使JSON成为理想的数据交换语言。 下面介绍四款处理json的java类库: Json-lib、Gson、Jackson、Fastjson FastJson Fastjson是一个Java语言编写的JSON处理器,由阿里巴巴公司开发。网址: https://github.com/alibaba/fastjson maven依赖配置: <dependency> <groupId>com.alibaba</groupId> <artifactId>fastjson</artifactId> <version>1.2.79</version> </dependency> 示例: public static String bean2Json(Object obj){ return JSON.toJSONString(obj); } VO vo = JSON.parseObject("...", VO.class); Json-lib JSON-lib is a java library for transforming beans, maps, collections, java arrays and XML to JSON and back again to beans and DynaBeans. 官网: http://json-lib.sourceforge.net/ ...

Created 31316-03-31 · Updated 9096-10-09 · 5 min · 957 words · -

SAX 解析和生成 XML 文档

SAX解析和生成XML文档 SAX解析和生成XML文档 分类: 【xml】 2013-09-24 22:37 2207人阅读 评论(6) 收藏 举报 生成解析xmljavasax 目录? 原创作品,允许转载,转载时请务必以超链接形式标明文章 原始出处 、作者信息和本人声明。否则将追究法律责任。 作者: 永恒の_☆ 地址: http://blog.csdn.net/chenghui0317/article/details/11990891 一、前言 SAX操作xml是基于事件来完成的,自己只负责调用解析的方法,然后具体解析操作都是交给DefaultHandler处理者来完成的,总的来说使用SAX解析和生成xml文档还是比较方便的 。 二、准备条件 因为SAX是jdk自带的解析方式,所以不用添加jar包引用。 三、使用SAX实战 解析xml文档 实现思路: <1>先由SAXParserFactory这个工厂的实例生产一个SAXParser解析器; <2>然后根据读取的xml路径,传递给SAXParser这个解析器,再调用parse()方法; <3>在parse()方法中需要传递DefaultHandler这个类的扩展类的实例,因为它才会真正去一步步去解析xml文档的; <4>在DefaultHandler扩展类中需要重写startDocument(),endDocument()等等方法,因为他们方法内部有返回的具体文档的结果。 具体代码如下: import java.io.BufferedOutputStream; import java.io.File; import java.io.FileInputStream; import java.io.FileNotFoundException; import java.io.FileOutputStream; import java.io.IOException; import java.io.InputStream; import java.util.ArrayList; import java.util.List; import javax.xml.parsers.ParserConfigurationException; import javax.xml.parsers.SAXParser; import javax.xml.parsers.SAXParserFactory; import javax.xml.transform.OutputKeys; import javax.xml.transform.Result; import javax.xml.transform.Transformer; import javax.xml.transform.TransformerConfigurationException; import javax.xml.transform.sax.SAXTransformerFactory; import javax.xml.transform.sax.TransformerHandler; import javax.xml.transform.stream.StreamResult; import org.xml.sax.Attributes; import org.xml.sax.InputSource; import org.xml.sax.SAXException; import org.xml.sax.helpers.AttributesImpl; import org.xml.sax.helpers.DefaultHandler; /** * 使用SAX操作xml的简单例子 * @author Administrator * */ public class SAXOperateXmlDemo { public void parseXml01(){ String xmlPath = "D:\\project\\dynamicWeb\\src\\resource\\user01.xml"; String xmlName = xmlPath.substring(xmlPath.lastIndexOf("\\")); try { //获取SAX分析器的工厂实例,专门负责创建SAXParser分析器 SAXParserFactory saxParserFactory = SAXParserFactory.newInstance(); //获取SAXParser分析器的实例 SAXParser saxParser = saxParserFactory.newSAXParser(); //和其他解析方式一样,也要间接通过InputStream输入流对象获取xml信息 //1、直接指定绝对路径获取文件输入流对象 //InputStream inputStream = new FileInputStream(xmlPath); //2、使用类的相对路径查找xml路径 //InputStream inputStream = this.getClass().getResourceAsStream(xmlName); //3、也可以指定路径完成InputStream输入流的实例化操作 InputStream inputStream = new FileInputStream(new File(xmlPath)); //4、使用InputSource输入源作为参数也可以转换xml //InputSource inputSource = new InputSource(inputStream); //解析xml文档 saxParser.parse(inputStream, new XmlSAXHandler01());//这里传递了自定义的XmlSAXHandler()管理者参数来解析xml,不像以前都是直接调用返回的Document对象 } catch (ParserConfigurationException e) { e.printStackTrace(); } catch (SAXException e) { e.printStackTrace(); } catch (FileNotFoundException e) { e.printStackTrace(); } catch (IOException e) { e.printStackTrace(); } } public static void main(String[] args) { SAXOperateXmlDemo demo = new SAXOperateXmlDemo(); demo.parseXml01(); } } /** * 解析SAX的处理者01 * @author Administrator * */ class XmlSAXHandler01 extends DefaultHandler { @Override public void startDocument() throws SAXException { System.out.println("-->startDocument() is invoked..."); super.startDocument(); } @Override public void endDocument() throws SAXException { System.out.println("-->endDocument() is invoked..."); super.endDocument(); } @Override public void startElement(String uri, String localName, String qName, Attributes attributes) throws SAXException { System.out.println("--->startElement() is invoked..."); super.startElement(uri, localName, qName, attributes); } @Override public void endElement(String uri, String localName, String qName) throws SAXException { System.out.println("--->endElement() is invoked..."); super.endElement(uri, localName, qName); } @Override public void characters(char[] ch, int start, int length) throws SAXException { System.out.println("---->characters() is invoked..."); super.characters(ch, start, length); } } 上面代码简单解析了一个xml,user01.xml文件的内容如下: ...

Created 1016-04-01 · Updated 9096-10-09 · 7 min · 1395 words · -

Jackson

Jackson Jackson 框架,轻易转换JSON Jackson可以轻松的将Java对象转换成json对象和xml文档,同样也可以将json、xml转换成Java对象。 前面有介绍过json-lib这个框架,在线博文: http://www.cnblogs.com/hoojo/archive/2011/04/21/2023805.html 相比json-lib框架,Jackson所依赖的jar包较少,简单易用并且性能也要相对高些。而且Jackson社区相对比较活跃,更新速度也比较快。 一、准备工作 下载依赖库jar包 Jackson的jar all下载地址: http://jackson.codehaus.org/1.7.6/jackson-all-1.7.6.jar 然后在工程中导入这个jar包即可开始工作 官方示例: http://wiki.fasterxml.com/JacksonInFiveMinutes 因为下面的程序是用junit测试用例运行的,所以还得添加junit的jar包。版本是junit-4.2.8 如果你需要转换xml,那么还需要stax2-api.jar 测试类基本代码如下 package com.hoo.test; import java.io.IOException; import java.io.StringWriter; import java.util.ArrayList; import java.util.HashMap; import java.util.Iterator; import java.util.LinkedHashMap; import java.util.List; import java.util.Map; import java.util.Set; import org.codehaus.jackson.JsonEncoding; import org.codehaus.jackson.JsonGenerationException; import org.codehaus.jackson.JsonGenerator; import org.codehaus.jackson.JsonParseException; import org.codehaus.jackson.map.JsonMappingException; import org.codehaus.jackson.map.ObjectMapper; import org.codehaus.jackson.node.JsonNodeFactory; import org.codehaus.jackson.xml.XmlMapper; import org.junit.After; import org.junit.Before; import org.junit.Test; import com.hoo.entity.AccountBean; /** function:Jackson 将java对象转换成JSON字符串,也可以将JSON字符串转换成java对象 jar-lib-version: jackson-all-1.6.2 jettison-1.0.1 @author hoojo @createDate 2010-11-23 下午04:54:53 ...

Created 4046-04-04 · Updated 9096-10-09 · 9 min · 1878 words · -

JVM 内存调优, OutOfMemoryError, StackOverflowError

OutOfMemoryError, StackOverflowError 这是IGT笔试的题目,分别写出可以造成两种错误的代码。由于之前测试过HashMap的容量的时候出现过内存不足的错误,所以能写出来,但StackOverflowError没什么印象了。 回来查了下StackOverflowError的资料,在德问社区上有人发帖子java产生StackOverflowError的原因是什么?询问: 请问java.lang.StackOverflowError产生的原因有什么? 已知的有死循环,循环的嵌套层数达到了环境的设定值 谢谢 有人回复说: 死循环本身是不会StackOverflow的,只有无限递归的时候会出现。原则上循环嵌套次数本身是没有限制的,限制的是占用的栈空间,如果你的函数里定义了很多很多变量,栈空间就会用完得比较快。 还有人讲的更详细: JVM里会有两种StackOverflowError, 一种是对应JVM stack, 一种是对应Native Method stack. 我们一般说的都是JVM stack. 每一个JVM线程维护自己的JVM stack. JVM stack里面存放 JVM栈帧. 栈帧中存放 数据和中间结果(本地变量数组, 操作符栈, 和对runtime 常量池的引用). 这些数据都比较小(对象都在堆中, 栈帧仅存放对象引用), 所以想单纯通过 在栈帧中存放大数据的方法 去引入StackOverflowError, 基本是不现实的.一般都是因为方法调用嵌套层数过大. http://docs.oracle.com/javase/specs/jvms/se7/html/jvms-2.html#jvms-2.5.2 JVM stack的大小是可以调节的, sun的windows jvm6 x64,jvm栈默认大小为1024k.可以通过-Xss1024k来调节. http://www.oracle.com/technetwork/java/hotspotfaq-138619.html#threads_oom 另外,在oracle的docsChapter 2. The Structure of the Java Virtual Machine中,有如下解释: Java Virtual Machine Stacks The following exceptional conditions are associated with Java Virtual Machine stacks: If the computation in a thread requires a larger Java Virtual Machine stack than is permitted, the Java Virtual Machine throws a StackOverflowError. ...

Created 9096-04-09 · Updated 9096-10-09 · 2 min · 407 words · -

Java 反编译工具:jad、jd-gui

Java反编译, jad, jd-gui Jadclipse JadClipse是Jad的Eclipse插件 jad jad是一款使用非常广泛地Java反编译工具,上面这款Jadclipse就是基于jad的反编译插件,JAD 文件包含 MIDlet 套件的标题信息,例如开发应用程序的公司、应用程序名称和大小。 官方网站: http://varaneckas.com/jad/ JD-GUI JD-GUI 是一个用 C++ 开发的 Java 反编译工具,由 Pavel Kouznetsov开发,支持Windows、Linux和苹果Mac Os三个平台。而且提供了Eclipse平台下的插件JD-Eclipse。JD-GUI不需要安装,直接点击运行,可以反编译jar,class文件。 官方网站: http://jd.benow.ca/ jdec http://jdec.sourceforge.net/ uuDeJava http://www.uuware.com/uudejava_cn.htm Minjava Java Decompiler http://jd.benow.ca/ 工具使用jad(还有joda,jd等工具) 使用jad反编译class文件,jad可以配置到eclipse中当做插件,直接下载jad的eclipse插件jar包,放在eclipse的plugin目录下即可。把下载的jad.exe放在JAVA_HOME的bin下。然后eclipse中点击class文件即可查看到源码。 使用其他工具,FrontEnd Plus集成了jad的java反编译工具,支持多个文件的反编译,也支持各种选项。 矫正反编译代码错误和奇怪代码 异常错误 反编译之后出入类似如下代码: DocumentException e; e; e.printStackTrace(); break MISSING_BLOCK_LABEL_67; e; e.printStackTrace(); break MISSING_BLOCK_LABEL_67; e; e.printStackTrace(); break MISSING_BLOCK_LABEL_67; e; 这种处理方式就是异常处理,反编译之后出现的这种情况,修改的时候使用try catch即可,其实完全可以将这块删除之后,然后eclipse会自动提示需要添加异常处理的模块,自动try catch即可。 语句标号 (goto) 这种情况常见于条件语句,即转化为if,else语句即可,这种比较容易判断。 i = 0; goto _L1 _L3: i++; _L1: if(i < 4) goto _L3; else goto_L2 ...

Created 11116-04-11 · Updated 9096-10-09 · 1 min · 198 words · -

Maven 中的 DependencyManagement 和 Dependencies

Maven中的DependencyManagement和Dependencies 这里介绍一个在父项目中的根结点中声明dependencyManagement和dependencies的区别 dependencyManagement Maven 使用dependencyManagement 元素来提供了一种管理依赖版本号的方式。通常会在一个组织或者项目的最顶层的父POM 中看到dependencyManagement 元素。使用pom.xml 中的dependencyManagement 元素能让 所有在子项目中引用一个依赖而不用显式的列出版本号。Maven 会沿着父子层次向上走,直到找到一个拥有dependencyManagement 元素的项目,然后它就会使用在这个dependencyManagement 元素中指定的版本号。 例如在父项目里: <dependencyManagement> <dependencies> <dependency> <groupId>MySQL</groupId> MySQL-connector-java</artifactId> <version>5.1.2</version> </dependency> ... <dependencies> </dependencyManagement> 然后在子项目里就可以添加MySQL-connector时可以不指定版本号,例如: <dependencies> <dependency> <groupId>MySQL</groupId> MySQL-connector-java</artifactId> </dependency> </dependencies> 这样做的好处就是: 如果有多个子项目都引用同一样依赖,则可以避免在每个使用的子项目里都声明一个版本号,这样当想升级或切换到另一个版本时,只需要在顶层父容器里更新,而不需要一个一个子项目的修改 ;另外如果某个子项目需要另外的一个版本,只需要声明version就可。 dependencyManagement里只是声明依赖,并不实现引入,因此子项目需要显式的声明需要用的依赖。 dependencies 相对于dependencyManagement,所有声明在dependencies里的依赖都会自动引入,并默认被所有的子项目继承。 classifier 如果你要发布同样的代码,但是由于技术原因需要生成两个单独的构件,你就要使用一个分类器 (classifier) 。例如,如果你想要构建两个单独的构件成JAR,一个使用Java 1.4 编译器,另一个使用Java 6 编译器,你就可以使用分类器 来生成两个单独的JAR构件,它们有同样的groupId:artifactId:version组合。如果你的项目使用本地扩展类库,你可以使用分类器为每一个目标平台生成一个构件。分类器常用于打包构件的源码,JavaDoc 或者二进制集合。 维护记录 时间 修改内容 原因 2026-10-09 修复本地 Hugo 构建的 Raw HTML 警告:代码/配置放入代码块,正文中的尖括号占位符改为行内代码;文件重命名为 maven-dependency-management.md;title 改为「Maven 中的 DependencyManagement 和 Dependencies」;url 改为 maven-dependency-management;旧 url 加入 aliases;categories 改为 Java 正文中的 HTML/XML 片段被当作原始 HTML 丢弃;文件名/URL/标题按规范调整

Created 28286-04-28 · Updated 9096-10-09 · 1 min · 77 words · -

maven pom

maven pom 基本内容: POM包括了所有的项目信息。 maven 相关: pom定义了最小的maven2元素,允许groupId,artifactId,version。所有需要的元素 groupId:项目或者组织的唯一标志,并且配置时生成的路径也是由此生成,如org.codehaus.mojo生成的相对路径为: /org/codehaus/mojo artifactId: 项目的通用名称 version:项目的版本 packaging: 打包的机制,如pom, jar, maven-plugin, ejb, war, ear, rar, par classifier: 分类 <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd"> <modelVersion>4.0.0</modelVersion> <groupId>com.wiloon</groupId> wechat</artifactId> <packaging>jar</packaging> <version>1.0-SNAPSHOT</version> <name>wechat</name> <url>http://maven.apache.org</url> <dependencies> <dependency> <groupId>junit</groupId> junit</artifactId> <version>3.8.1</version> <scope>test</scope> </dependency> </dependencies> </project> compile plugin, war plugin, specify jdk version <build> <plugins> <plugin> <groupId>org.apache.maven.plugins</groupId> maven-compiler-plugin</artifactId> <configuration> <source>1.7</source> <target>1.7</target> </configuration> </plugin> <plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-war-plugin</artifactId> </plugin> </plugins> </build> 维护记录 时间 修改内容 原因 2026-10-09 修复本地 Hugo 构建的 Raw HTML 警告:代码/配置放入代码块,正文中的尖括号占位符改为行内代码;categories 改为 Java 正文中的 HTML/XML 片段被当作原始 HTML 丢弃;文件名/URL/标题按规范调整

Created 30306-04-30 · Updated 9096-10-09 · 1 min · 85 words · -

命令行创建多模块的 Maven 项目 (父模块, 子模块)

命令行 创建多模块的Maven项目(父模块,子模块) 我们都知道,我们常常将一个复杂的java应用拆分成多个java子应用。由于maven的出现,这种拆分就更加容易了,因为我们通过maven可以创建多个关联模块的项目 (Multiple Module Projects) 。由一个总的模块,下面包含多个子模块 (子模块还可以包含子模块) 。 一、通过在Maven命令行创建。 创建父模块 (总的POM) - cms-validator 使用命令mvn archetype:create -DgroupId=com.ebay.tools.cms.validator -DartifactId=cms-validator 创建一个maven项目,然后修改该项目的pom.xml文件,将package类型改为pom <packaging>pom</packaging> 并删除其中的src目录。 cd cms-validator 创建提供rest service的子模块: validator-rest 在父模块的目录下, 使用命令mvn archetype:create -DgroupId=com.ebay.tools.cms.validator.rest -DartifactId=validator-rest 创建一个maven (子) 项目。 创建一个web子模块: validator-web 在父模块的目录下, mvn archetype:create -DgroupId=com.ebay.tools.cms.validator.web -DartifactId=validator-web -DarchetypeArtifactId=maven-archetype-webapp 完成以上3步以后,会在总的pom.xml中已经自动加入: <modules> <module>validator-rest</module> <module>validator-web</module> </modules> 在各个子模块中也自动的加入了: <parent> <artifactId>cms-validator</artifactId> <groupId>com.ebay.tools.cms.validator</groupId> <version>1.0-SNAPSHOT</version> </parent> 由于默认情况下子模块继承了总POM的package(pom),这里需要修改子模块的pom的package类型。 validator-web模块覆盖为<packaging>war</packaging>, validator-rest模块修改为: <packaging>jar</packaging>。 对父模块的特别设置: 需要在上级模块中设置java编译的参数,现在eclipse一般都使用比较新的版本,默认jdk是1.6,而maven默认的Jdk版本很有可能还是1.4。 所以需要设置java编译参数。 <plugin> <artifactId>maven-compiler-plugin</artifactId> <configuration> <source>1.6</source> <target>1.6</target> <encoding>UTF-8</encoding> </configuration> </plugin> 如果web子模块需要wtp的支持,则可以在web模块的pom中设置wtp的支持,需要设置elcipse插件: <build> <plugins> <plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-eclipse-plugin</artifactId> <configuration> <wtpmanifest>true</wtpmanifest> <wtpapplicationxml>true</wtpapplicationxml> <wtpversion>2.0</wtpversion> </configuration> </plugin> </plugins> </build> 生成eclipse项目: 在父模块的根目录下,执行命令: ...

Created 6066-05-06 · Updated 9096-10-09 · 1 min · 137 words · -

MyBatis 实体属性与表字段名不一致

MyBatis_当实体属性与表字段名不一致 http://m.blog.csdn.net/blog/wuqinfei_cs/12873135 映射 /* <!-- 将表字段与实体属性一一对应 --> <resultMap type="com.hehe.mybatis.domain.User" id="userMap"> <id column="id" property="id"/> <result column="name" property="username"/> <result column="address" property="uaddress"/> </resultMap> <select id="selectUserById" parameterType="string" resultMap="userMap"> select * from user where id = #{id} </select> 维护记录 时间 修改内容 原因 2026-10-09 修复本地 Hugo 构建的 Raw HTML 警告:代码/配置放入代码块,正文中的尖括号占位符改为行内代码;文件重命名为 mybatis-result-map.md;title 改为「MyBatis 实体属性与表字段名不一致」;url 改为 mybatis-result-map;旧 url 加入 aliases;categories 改为 Java 正文中的 HTML/XML 片段被当作原始 HTML 丢弃;文件名/URL/标题按规范调整

Created 7076-05-07 · Updated 9096-10-09 · 1 min · 59 words · -

maven setting, mirror, repository

maven setting, mirror, repository maven mirror, repository mirror和 repository 1 Repository (仓库) 1.1 Maven仓库主要有2种: remote repository: 相当于公共的仓库,大家都能访问到,一般可以用URL的形式访问 local repository: 存放在本地磁盘的一个文件夹,例如,windows上默认是C:\Users\{用户名}.m2\repository目录 1.2 Remote Repository主要有3种: 中央仓库: http://repo1.maven.org/maven2/ 私服: 内网自建的maven repository,其URL是一个内部网址 其他公共仓库: 其他可以互联网公共访问maven repository,例如 jboss repository等 repository里存放的都是各种jar包和maven插件。当向仓库请求插件或依赖的时候,会先检查local repository,如果local repository有则直接返回,否则会向remote repository请求,并缓存到local repository。也可以把做的东西放到本地仓库,仅供本地使用;或上传到远程仓库,供大家使用。 2 Mirror mirror相当于一个拦截器,它会拦截maven对remote repository的相关请求,把请求里的remote repository地址,重定向到mirror里配置的地址。 2.1 没有配置mirror: 2.2 配置mirror: 此时,B Repository被称为A Repository的镜像。 如果仓库X可以提供仓库Y存储的所有内容,那么就可以认为X是Y的一个镜像。换句话说,任何一个可以从仓库Y获得的构件,都胡够从它的镜像中获取。 2.3 <mirrorOf></mirrorOf> <mirrorOf></mirrorOf>标签里面放置的是要被镜像的Repository ID。为了满足一些复杂的需求,Maven还支持更高级的镜像配置: <mirrorOf>*</mirrorOf> 匹配所有远程仓库。 <mirrorOf>repo1,repo2</mirrorOf> 匹配仓库repo1和repo2,使用逗号分隔多个远程仓库。 <mirrorOf>*,!repo1</mirrorOf> 匹配所有远程仓库,repo1除外,使用感叹号将仓库从匹配中排除。 3 Repository与Mirror 3.1 定义 其实,mirror表示的是两个Repository之间的关系,在maven配置文件 (setting.xml)里配置了<mirrors><mirror>……….</mirror></mirrors>,即定义了两个Repository之间的镜像关系。 3.2 目的 配置两个Repository之间的镜像关系,一般是出于访问速度和下载速度考虑。 例如, 有一个项目,需要在公司和住所都编码,并在项目pom.xml配置了A Maven库。在公司,是电信网络,访问A库很快,所以maven管理依赖和插件都从A库下载;在住所,是网通网络,访问A库很慢,但是访问B库很快。这时,在住所的setting.xml里,只要配置一下<mirrors><mirror>….</mirror></mirrors>,让B库成为A库的mirror,即可不用更改项目pom.xml里对于A库的相关配置。 ...

Created 18186-05-18 · Updated 9096-10-09 · 2 min · 234 words · -

Maven 构建之依赖传递

Maven构建之依赖传递 http://a123159521.iteye.com/blog/774322 博客分类: Maven mavenjunit项目管理配置管理Apache 如果断Maven的依赖构建必须每一个项目都指定,那配置是累死人了,比如A依赖了20个项目,B依赖A,那么还要添加20个项目,那就悲剧了,maven有依赖传递的功能。 Transitive Dependency (传递依赖) 你的项目依赖于A,A又依赖于B。你的项目是否要声明你依赖于B? Maven的回答是它帮你自动管理这种依赖的传递,你不需要声明你依赖于B,由Maven来做。 [版本还是要自己指定的.] Dependency Scope (依赖范围) 因此,Maven考虑了6中可能的scope供选择: compile: 默认的scope。编译、测试、打包全都需要。compile参与依赖传递,就是说,你的项目A依赖于B(依赖scope是compile),项目C依赖于你的项目A,那么C也就依赖于B。 provided: 表示JDK或者容器会在Runtime时提供这些(jar),如上面说到的servlet api。provided的东西在编译和测试时会用到,不参与传递依赖。 runtime: 表示编译时不需要,但测试和运行时需要,最终打包时会包含进去。 test: 只用于测试阶段 (测试的编译和测试的运行) ,典型的就是junit的jar。 system: 和provided类似,但要求jar是你的系统里已有的,不会在repository里找,如rt.jar,tools.jar这些。 import: 简单的说,你的项目的pom可以继承另一个项目的pom,从而继承了父项目的依赖关系,但是因为之后single inheritance的限制,所以创造了import,使得你可以"导入"或者说"继承"任何一到多个项目的依赖关系。 依赖管理(dependencyManagement) 实际的项目中,你会有一大把的Maven模块,而且你往往发现这些模块有很多依赖是完全项目的,A模块有个对spring的依赖,B模块也有,它们的依赖配置一模一样,同样的groupId, artifactId, version,或者还有exclusions, classifer。细心的分会发现这是一种重复,重复就意味着潜在的问题,Maven提供的dependencyManagement就是用来消除这种重复的。 为了实现项目间的依赖,一般情况下,web项目依赖于app项目,而app项目很可能依赖于其他的app项目,比如我建了一个util项目,app依赖于util,那么webapp也需要依赖于util,但是我不配置webapp依赖util,验证一下,会不会自动加载依赖包. util项目的构建请参照前讲,接下来看maven配置: util配置; <?xml version="1.0" encoding="UTF-8"?> <project xsi:schemaLocation="<http://maven.apache.org/POM/4.0.0> [http://maven.apache.org/xsd/maven-4.0.0.xsd](http://maven.apache.org/xsd/maven-4.0.0.xsd)" xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"> <modelVersion>4.0.0</modelVersion> <parent> demo</artifactId> <groupId>com.test</groupId> <version>1.0.0-SNAPSHOT</version> </parent> <groupId>com.test.util</groupId> util</artifactId> <version>1.0-SNAPSHOT</version> <name>util</name> <url><http://maven.apache.org>[/url](/url) <build> <plugins> <plugin> <groupId>org.apache.maven.plugins</groupId> maven-compiler-plugin</artifactId> <configuration> <source>1.6</source> <target>1.6</target> </configuration> </plugin> </plugins> </build> <dependencies> <dependency> <groupId>junit</groupId> junit</artifactId> <version>3.8.1</version> <scope>test</scope> </dependency> </dependencies> <properties> <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding> </properties> </project> app项目的maven配置: ...

Created 28286-05-28 · Updated 9096-10-09 · 2 min · 268 words · -

jpa annotation, 注解

jpa annotation, 注解 http://mzhj.iteye.com/blog/711685 @Embedded 你可以创建一个类被嵌套在实体类中,在这种情况下我们可以使用@Embedded注解。例如,在Hotel类中 可能会有一个Address。 Address是Hotel不可分割的一部分,没有ID, 并且不会被存储在分开的collection中。在这种情况下我们可以使用@Embedded注解 @Entity 标识这个pojo是一个jpa实体 Specifies that the class is an entity. This annotation is applied to the entity class. @Table (name= users ) //指定表名为users @Column @Column(name="DESC", nullable=false, length=512) 设置字段类型 通过@Column注解设置,包含的设置如下 .name: 字段名 .unique: 是否唯一 .nullable: 是否可以为空 .inserttable: 是否可以插入 .updateable: 是否可以更新 .columnDefinition: 定义建表时创建此列的DDL .secondaryTable: 从表名。如果此列不建在主表上 (默认建在主表) ,该属性定义该列所在从表的名字。 @Column(name = "user_code", nullable = false, length=32)//设置属性userCode对应的字段为user_code,长度为32,非空 private String userCode; @Column(name = "user_wages", nullable = true, precision=12, scale=2)//设置属性wages对应的字段为user_wages,12位数字可保留两位小数,可以为空 private double wages; @Temporal(TemporalType.DATE)//设置为时间类型 private Date joinDate; @Id 设置主键 ...

Created 28286-05-28 · Updated 9096-10-09 · 3 min · 508 words · -

JPA 的 persistence.xml 文件

JPA的persistence.xml文件 Posted on 2012-05-24 12:27 CN.programmer.Luxh 阅读(7217) 评论(0) 编辑 收藏 persistence.xml文件必须定义在classpath路径下的META-INF文件夹中。 我们看看基于Hibernate提供的一个比较完整的JPA2.0的persistence.xml文件。 persistence.xml: 1 <?xml version="1.0" encoding="UTF-8"?> 2 <persistence version="2.0" xmlns="http://java.sun.com/xml/ns/persistence" 3 xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 4 xsi:schemaLocation="http://java.sun.com/xml/ns/persistence 5 http://java.sun.com/xml/ns/persistence/persistence_2_0.xsd"> 7 <!-必须要有name属性,不能为空 -> 8 <persistence-unit name="jpaPU" transaction-type="RESOURCE_LOCAL"> 9 <!-可选 -> 10 <provider>org.hibernate.ejb.HibernatePersistence</provider> 11 <!-可选 -> 12 <jta-data-source>java:/DefaultDS</jta-data-source> 13 <!-可选 -> 14 <mapping-file>ormap.xml</mapping-file> 15 <!-可选 -> 16 <jar-file>MyApp.jar</jar-file> 17 <!-可选 -> 18 <class>org.acme.Employee</class> 19 <!-可选 -> 20 <shared-cache-mode>ENABLE_SELECTOVE</shared-cache-mode> 21 <!-可选 -> 22 <validation-mode>CALLBACK</validation-mode> 24 <!-厂商的特定属性 -> 25 <properties> 26 <!-配置Hibernate方言 -> 27 <property name="hibernate.dialect" value="org.hibernate.dialect.MySQL5Dialect" /> 28 <!-配置数据库驱动 -> 29 <property name="hibernate.connection.driver_class" value="com.MySQL.jdbc.Driver" /> 30 <!-配置数据库用户名 -> 31 <property name="hibernate.connection.username" value="root" /> 32 <!-配置数据库密码 -> 33 <property name="hibernate.connection.password" value="root" /> 34 <!-配置数据库url -> 35 <property name="hibernate.connection.url" value="jdbc:MySQL://localhost:3306/jpa?useUnicode=true&characterEncoding=UTF-8" /> 36 <!-设置外连接抓取树的最大深度 -> 37 <property name="hibernate.max_fetch_depth" value="3" /> 38 <!-自动输出schema创建DDL语句 -> 39 <property name="hibernate.hbm2ddl.auto" value="update" /> 40 </properties> 41 </persistence-unit> 43 </persistence> xsi:schemaLocation="http://java.sun.com/xml/ns/persistence http://java.sun.com/xml/ns/persistence/persistence_2_0.xsd" 要注意使用的是2.0规范 ...

Created 29296-05-29 · Updated 9096-10-09 · 2 min · 225 words · -

Spring 生成 EntityManagerFactory 的三种方式

spring生成EntityManagerFactory的三种方式 1.LocalEntityManagerFactoryBean 只是简单环境中使用。它使用JPA PersistenceProvider自动检测机制( according to JPA’s Java SE bootstrapping ),并且大多数情况下,你只能定义一下persistence unit name 例如: <beans> <bean id="myEmf" class="org.springframework.orm.jpa.LocalEntityManagerFactoryBean"> <property name="persistenceUnitName" value="myPersistenceUnit"/> </bean> </beans> 2.从JNDI获取EntityManagerFactory 这个选项是当你应用发布在javaee5的服务器中。你可以参阅自己应用服务器文档,如何发布一个自定义的JPA provider到你的应用服务器中。 例: <beans> <jee:jndi-lookup id="myEmf" jndi-name="persistence/myPersistenceUnit"/> </beans> 当javaee服务器启动时,会自动检测persistence units。实际上,是检测应用包中的META-INF/persistence.xml 文件和web.xml中的persistence-unit-ref,以及定义的environment naming。我理解就是JNDI的name。 一般应用情景是: 在META-INF/persistence.xml中 使用<jta-data-source>java:/ MySQLDS</jta-data-source> 获取容器发布的Datesource。 transactions是使用的javaee容器支持的JTA系统,例如tomcat中,可以这样 如果你的项目准备部署在tomcat上,要支持jta,则需把相关的包放在tomcat/lib包下 jndi配置,可以把jndi的配置放置在 tomcat/conf/Catalina/域名(如localhost)/项目名.xml 文件的Context节点下,如下: <Resource name="" auth="Container" type="javax.sql.DataSource" username="" password="" driveClassName="oracle.jdbc.driver.OracleDriver" url="" maxActive="45" maxIdle="25"/> jndi也可以配置在server.xml,context.xml中 2)jta UserTransaction配置 在server.xml文件GlobalNamingResources节点下配置如下: <!- Resource configuration for UserTransaction use JOTM -> <Resource name="UserTransaction" auth="Container" type="javax.transaction.UserTransaction" factory="org.objectweb.jotm.UserTransactionFactory" jotm.timeout="60"/> 然后在 项目名.xml 文件的context节点下加: <ResourceLink name="UserTransaction" global="UserTransaction" type="javax.transaction.UserTransaction"/> SPRING 仅仅做的是是把EntityManagerFactory通过依赖注入到应用的object中。如果要管理事务,则使用JtaTransactionManager。 3.LocalContainerEntityManagerFactoryBean ...

Created 29296-05-29 · Updated 9096-10-09 · 2 min · 291 words · -

JPA JPQL

JPA JPQL http://flowercat.iteye.com/blog/667773 max result entityManager.createQuery(SQL_QUERY).setParameter(arg0,arg1).setMaxResults(10).getResultList(); JPQL就是一种查询语言,具有与 SQL 相 类似的特征, JPQL 是完全面向对象的,具备继承、多态和关联等特性,和hibernate HQL很相似。 查询语句的参数 JPQL 语句支持两种方式的参数定义方式 : 命名参数和位置参数 。 。在同一个查 询语句中只允许使用一种参数定义方式。 命令参数的格式为: " : + 参数 名" 例: Query query = em.createQuery(“select p from Person p where p.personid=:Id “); query.setParameter(“Id”,new Integer(1)); 位置参数的格式为” ?+ 位置编号” 例: Query query = em.createQuery(“select p from Person p where p.personid=?1 “); query.setParameter(1,new Integer(1)); 如果你需要传递 java.util.Date 或 java.util.Calendar 参数进一个参数查询 ,你需要使用一个特殊的 setParameter() 方法 ,相关的 setParameter 方法定义如下: public interface Query ...

Created 6066-06-06 · Updated 9096-10-09 · 8 min · 1526 words · -

java openjdk JMH

java openjdk JMH create test project with maven mvn archetype:generate \ -DinteractiveMode=false \ -DarchetypeGroupId=org.openjdk.jmh \ -DarchetypeArtifactId=jmh-java-benchmark-archetype \ -DgroupId=org.sample \ -DartifactId=test \ -Dversion=1.0 JMH 是一个由 OpenJDK/Oracle 里面那群开发了 Java 编译器的大牛们所开发的 Micro Benchmark Framework 。何谓 Micro Benchmark 呢?简单地说就是在 method 层面上的 benchmark,精度可以精确到微秒级。可以看出 JMH 主要使用在当你已经找出了热点函数,而需要对热点函数进行进一步的优化时,就可以使用 JMH 对优化的效果进行定量的分析。 比较典型的使用场景还有: 想定量地知道某个函数需要执行多长时间,以及执行时间和输入 n 的相关性 一个函数有两种不同实现 (例如实现 A 使用了 FixedThreadPool,实现 B 使用了 ForkJoinPool) ,不知道哪种实现性能更好 尽管 JMH 是一个相当不错的 Micro Benchmark Framework,但很无奈的是网上能够找到的文档比较少,而官方也没有提供比较详细的文档,对使用造成了一定的障碍。但是有个好消息是官方的 Code Sample 写得非常浅显易懂,推荐在需要详细了解 JMH 的用法时可以通读一遍——本文则会介绍 JMH 最典型的用法和部分常用选项。 第一个例子 如果你使用 maven 来管理你的 Java 项目的话,引入 JMH 是一件很简单的事情——只需要在 pom.xml 里增加 JMH 的依赖即可<properties> <jmh.version>1.14.1</jmh.version> </properties> ...

Created 3036-09-03 · Updated 9096-10-09 · 5 min · 910 words · -