mirror of
https://github.com/Estom/notes.git
synced 2026-02-06 12:04:05 +08:00
Java内容重新整理删除过期的东西
This commit is contained in:
@@ -0,0 +1,25 @@
|
||||
package cn.aofeng.demo.java.lang.instrument;
|
||||
|
||||
import java.lang.instrument.Instrumentation;
|
||||
|
||||
import org.apache.commons.lang.StringUtils;
|
||||
|
||||
import cn.aofeng.demo.util.LogUtil;
|
||||
|
||||
/**
|
||||
* Instrument入口类。
|
||||
*
|
||||
* @author <a href="mailto:aofengblog@163.com">聂勇</a>
|
||||
*/
|
||||
public class FirstInstrumentation {
|
||||
|
||||
public static void premain(String options, Instrumentation ins) {
|
||||
if (StringUtils.isBlank(options)) {
|
||||
LogUtil.log("instrument without options");
|
||||
} else {
|
||||
LogUtil.log("instrument with options:%s", options);
|
||||
}
|
||||
|
||||
ins.addTransformer(new FirstTransformer());
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,26 @@
|
||||
/**
|
||||
*
|
||||
*/
|
||||
package cn.aofeng.demo.java.lang.instrument;
|
||||
|
||||
import java.lang.instrument.ClassFileTransformer;
|
||||
import java.lang.instrument.IllegalClassFormatException;
|
||||
import java.security.ProtectionDomain;
|
||||
|
||||
import cn.aofeng.demo.util.LogUtil;
|
||||
|
||||
/**
|
||||
* 只输出问候语,不进行字节码修改的Class转换器。
|
||||
*
|
||||
* @author <a href="mailto:aofengblog@163.com">聂勇</a>
|
||||
*/
|
||||
public class FirstTransformer implements ClassFileTransformer {
|
||||
|
||||
@Override
|
||||
public byte[] transform(ClassLoader loader, String className, Class<?> classBeingRedefined,
|
||||
ProtectionDomain protectionDomain, byte[] classfileBuffer) throws IllegalClassFormatException {
|
||||
LogUtil.log(">>> %s", className);
|
||||
return null;
|
||||
}
|
||||
|
||||
}
|
||||
14
Java/JavaDemo/codedemo/java/lang/instrument/Hello.java
Normal file
14
Java/JavaDemo/codedemo/java/lang/instrument/Hello.java
Normal file
@@ -0,0 +1,14 @@
|
||||
package cn.aofeng.demo.java.lang.instrument;
|
||||
|
||||
/**
|
||||
* Instrumentation启动类。 *
|
||||
*
|
||||
* @author <a href="mailto:aofengblog@163.com">聂勇</a>
|
||||
*/
|
||||
public class Hello {
|
||||
|
||||
public static void main(String[] args) {
|
||||
// nothing
|
||||
}
|
||||
|
||||
}
|
||||
40
Java/JavaDemo/codedemo/java/lang/instrument/README.md
Normal file
40
Java/JavaDemo/codedemo/java/lang/instrument/README.md
Normal file
@@ -0,0 +1,40 @@
|
||||
# 一、Instrumentation入门
|
||||
|
||||
* [FirstTransformer.java](FirstTransformer.java) 处理字节码,由类FirstInstrumentation执行
|
||||
* [FirstInstrumentation.java](FirstInstrumentation.java) instrumentation入口类,由javaagent载入执行
|
||||
* [build.xml](build.xml) Ant脚本,负责编译、打包和运行
|
||||
|
||||
在当前目录下执行命令:
|
||||
```bash
|
||||
ant
|
||||
```
|
||||
|
||||
输出信息如下:
|
||||
> [java] instrument with options:"Hello, Instrumentation"
|
||||
> [java] >>> java/lang/invoke/MethodHandleImpl
|
||||
> [java] >>> java/lang/invoke/MethodHandleImpl$1
|
||||
> [java] >>> java/lang/invoke/MethodHandleImpl$2
|
||||
> [java] >>> java/util/function/Function
|
||||
> [java] >>> java/lang/invoke/MethodHandleImpl$3
|
||||
> [java] >>> java/lang/invoke/MethodHandleImpl$4
|
||||
> [java] >>> java/lang/ClassValue
|
||||
> [java] >>> java/lang/ClassValue$Entry
|
||||
> [java] >>> java/lang/ClassValue$Identity
|
||||
> [java] >>> java/lang/ClassValue$Version
|
||||
> [java] >>> java/lang/invoke/MemberName$Factory
|
||||
> [java] >>> java/lang/invoke/MethodHandleStatics
|
||||
> [java] >>> java/lang/invoke/MethodHandleStatics$1
|
||||
> [java] >>> sun/misc/PostVMInitHook
|
||||
> [java] >>> sun/usagetracker/UsageTrackerClient
|
||||
> [java] >>> java/util/concurrent/atomic/AtomicBoolean
|
||||
> [java] >>> sun/usagetracker/UsageTrackerClient$1
|
||||
> [java] >>> sun/usagetracker/UsageTrackerClient$4
|
||||
> [java] >>> sun/usagetracker/UsageTrackerClient$3
|
||||
> [java] >>> java/io/FileOutputStream$1
|
||||
> [java] >>> sun/launcher/LauncherHelper
|
||||
> [java] >>> cn/aofeng/demo/java/lang/instrument/Hello
|
||||
> [java] >>> sun/launcher/LauncherHelper$FXHelper
|
||||
> [java] >>> java/lang/Class$MethodArray
|
||||
> [java] >>> java/lang/Void
|
||||
> [java] >>> java/lang/Shutdown
|
||||
> [java] >>> java/lang/Shutdown$Lock
|
||||
57
Java/JavaDemo/codedemo/java/lang/instrument/build.xml
Normal file
57
Java/JavaDemo/codedemo/java/lang/instrument/build.xml
Normal file
@@ -0,0 +1,57 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project name="Instrumentation" default="run" basedir="../../../../../../../">
|
||||
|
||||
<property name="project.src.dir" value="${basedir}/src" />
|
||||
<property name="project.lib.dir" value="${basedir}/lib" />
|
||||
<property name="project.conf.dir" value="${basedir}/conf" />
|
||||
<property name="project.target.dir" value="${basedir}/classes" />
|
||||
<property name="project.dist.dir" value="${basedir}/dist" />
|
||||
|
||||
<path id="project.classpath">
|
||||
<fileset dir="${project.lib.dir}">
|
||||
<include name="*.jar" />
|
||||
</fileset>
|
||||
</path>
|
||||
|
||||
<target name="prepare">
|
||||
<delete dir="${project.target.dir}" />
|
||||
<mkdir dir="${project.target.dir}"/>
|
||||
<copy todir="${project.target.dir}">
|
||||
<fileset dir="${project.conf.dir}">
|
||||
<include name="**/*.properties" />
|
||||
<include name="**/*.xml" />
|
||||
</fileset>
|
||||
</copy>
|
||||
|
||||
<delete dir="${project.dist.dir}" />
|
||||
<mkdir dir="${project.dist.dir}" />
|
||||
</target>
|
||||
|
||||
<target name="compileWithJavac" depends="prepare">
|
||||
<echo message="compile with javac" />
|
||||
<javac destdir="${project.target.dir}" srcdir="${project.src.dir}" source="1.8" target="1.8"
|
||||
encoding="UTF-8" debug="true" includeantruntime="false">
|
||||
<classpath refid="project.classpath" />
|
||||
</javac>
|
||||
</target>
|
||||
|
||||
<target name="package" depends="compileWithJavac">
|
||||
<jar destfile="${project.dist.dir}/hello.jar">
|
||||
<fileset dir="${project.target.dir}">
|
||||
<include name="cn/aofeng/demo/java/lang/instrument/*.class" />
|
||||
</fileset>
|
||||
<manifest>
|
||||
<attribute name="Premain-Class" value="cn.aofeng.demo.java.lang.instrument.FirstInstrumentation" />
|
||||
</manifest>
|
||||
</jar>
|
||||
</target>
|
||||
|
||||
<target name="run" depends="package">
|
||||
<java classname="cn.aofeng.demo.java.lang.instrument.Hello" fork="true">
|
||||
<classpath refid="project.classpath" />
|
||||
<classpath location="${project.target.dir}" />
|
||||
<jvmarg value="-javaagent:${project.dist.dir}/hello.jar="Hello, Instrumentation"" />
|
||||
</java>
|
||||
</target>
|
||||
|
||||
</project>
|
||||
143
Java/JavaDemo/codedemo/java/lang/reflect/ClassAnalyze.java
Normal file
143
Java/JavaDemo/codedemo/java/lang/reflect/ClassAnalyze.java
Normal file
@@ -0,0 +1,143 @@
|
||||
package cn.aofeng.demo.java.lang.reflect;
|
||||
|
||||
import java.lang.annotation.Annotation;
|
||||
import java.lang.reflect.AnnotatedElement;
|
||||
import java.lang.reflect.Constructor;
|
||||
import java.lang.reflect.Field;
|
||||
import java.lang.reflect.Member;
|
||||
import java.lang.reflect.Method;
|
||||
import java.lang.reflect.Modifier;
|
||||
|
||||
/**
|
||||
* 通过反射获取类的构造方法、字段、方法和注解等信息。
|
||||
*
|
||||
* @author <a href="mailto:aofengblog@163.com">聂勇</a>
|
||||
*/
|
||||
public class ClassAnalyze {
|
||||
|
||||
final static String PREFIX = "==========";
|
||||
final static String SUFFIX = PREFIX;
|
||||
|
||||
private static void parseClass(Class<?> claz) {
|
||||
// 注解
|
||||
parseAnnotation(claz);
|
||||
|
||||
// 类
|
||||
StringBuilder buffer = new StringBuilder(32)
|
||||
.append( Modifier.toString(claz.getModifiers()) )
|
||||
.append(' ')
|
||||
.append(claz.getName());
|
||||
log(buffer.toString());
|
||||
}
|
||||
|
||||
private static void parseConstructor(Constructor<?> c) {
|
||||
// 注解
|
||||
parseAnnotation(c);
|
||||
|
||||
// 构造方法
|
||||
StringBuilder buffer = new StringBuilder(32)
|
||||
.append( parseMember(c) )
|
||||
.append('(');
|
||||
|
||||
// 参数
|
||||
Class<?>[] params = c.getParameterTypes();
|
||||
for (int index = 0; index < params.length; index++) {
|
||||
buffer.append(params[index].getName());
|
||||
if (index!=params.length-1) {
|
||||
buffer.append(", ");
|
||||
}
|
||||
}
|
||||
buffer.append(')');
|
||||
|
||||
log(buffer.toString());
|
||||
}
|
||||
|
||||
private static void parseMethod(Method method) {
|
||||
// 注解
|
||||
parseAnnotation(method);
|
||||
|
||||
// 方法
|
||||
StringBuilder buffer = new StringBuilder(32)
|
||||
.append( parseMember(method) )
|
||||
.append('(');
|
||||
|
||||
// 参数
|
||||
Class<?>[] params = method.getParameterTypes();
|
||||
for (int index = 0; index < params.length; index++) {
|
||||
buffer.append(params[index].getName());
|
||||
if (index!=params.length-1) {
|
||||
buffer.append(", ");
|
||||
}
|
||||
}
|
||||
buffer.append(')');
|
||||
|
||||
log(buffer.toString());
|
||||
}
|
||||
|
||||
private static void parseField(Field field) {
|
||||
// 注解
|
||||
parseAnnotation(field);
|
||||
|
||||
// 字段
|
||||
StringBuilder buffer = parseMember(field);
|
||||
log(buffer.toString());
|
||||
}
|
||||
|
||||
/**
|
||||
* 解析方法、字段或构造方法的信息。
|
||||
* @param member 方法、字段或构造方法
|
||||
* @return 修饰符和名称组成的字符串。
|
||||
*/
|
||||
private static StringBuilder parseMember(Member member) {
|
||||
StringBuilder buffer = new StringBuilder()
|
||||
.append(Modifier.toString(member.getModifiers()))
|
||||
.append(' ')
|
||||
.append(member.getName());
|
||||
return buffer;
|
||||
}
|
||||
|
||||
/**
|
||||
* 解析注解信息。
|
||||
*/
|
||||
private static void parseAnnotation(AnnotatedElement ae) {
|
||||
Annotation[] ans = ae.getDeclaredAnnotations();
|
||||
for (Annotation annotation : ans) {
|
||||
log(annotation.toString());
|
||||
}
|
||||
}
|
||||
|
||||
public static void log(String msg, Object... param) {
|
||||
System.out.println( String.format(msg, param) );
|
||||
}
|
||||
|
||||
public static void main(String[] args) throws ClassNotFoundException {
|
||||
if (args.length != 1) {
|
||||
log("无效的输入参数!");
|
||||
log("示例:");
|
||||
log("java cn.aofeng.demo.java.lang.reflect.ClassAnalyze java.util.HashMap");
|
||||
}
|
||||
Class<?> claz = Class.forName(args[0]);
|
||||
|
||||
log("%s类%s", PREFIX, SUFFIX);
|
||||
parseClass(claz);
|
||||
|
||||
log("%s构造方法%s", PREFIX, SUFFIX);
|
||||
Constructor<?>[] cs = claz.getDeclaredConstructors();
|
||||
for (Constructor<?> constructor : cs) {
|
||||
parseConstructor(constructor);
|
||||
}
|
||||
|
||||
log("%s字段%s", PREFIX, SUFFIX);
|
||||
Field[] fields = claz.getDeclaredFields();
|
||||
for (Field field : fields) {
|
||||
parseField(field);
|
||||
}
|
||||
|
||||
log("%s方法%s", PREFIX, SUFFIX);
|
||||
Method[] methods = claz.getDeclaredMethods();
|
||||
for (Method method : methods) {
|
||||
parseMethod(method);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
36
Java/JavaDemo/codedemo/java/lang/reflect/CreateInstance.java
Normal file
36
Java/JavaDemo/codedemo/java/lang/reflect/CreateInstance.java
Normal file
@@ -0,0 +1,36 @@
|
||||
package cn.aofeng.demo.java.lang.reflect;
|
||||
|
||||
import java.lang.reflect.Constructor;
|
||||
import java.lang.reflect.InvocationTargetException;
|
||||
|
||||
import cn.aofeng.demo.util.LogUtil;
|
||||
|
||||
/**
|
||||
* 通过反射使用构造方法创建对象实例。
|
||||
*
|
||||
* @author <a href="mailto:aofengblog@163.com">聂勇</a>
|
||||
*/
|
||||
public class CreateInstance {
|
||||
|
||||
public static void main(String[] args) throws InstantiationException, IllegalAccessException,
|
||||
NoSuchMethodException, SecurityException,
|
||||
IllegalArgumentException, InvocationTargetException {
|
||||
Class<Man> claz = Man.class;
|
||||
|
||||
// 调用默认的public构造方法
|
||||
Man man = claz.newInstance();
|
||||
LogUtil.log(man.toString());
|
||||
|
||||
// 调用带参数的protected构造方法
|
||||
Constructor<Man> manC = claz.getDeclaredConstructor(String.class);
|
||||
man = manC.newInstance("aofeng");
|
||||
LogUtil.log(man.toString());
|
||||
|
||||
// 调用带参数的private构造方法
|
||||
manC = claz.getDeclaredConstructor(String.class, int.class);
|
||||
manC.setAccessible(true);
|
||||
man = manC.newInstance("NieYong", 32);
|
||||
LogUtil.log(man.toString());
|
||||
}
|
||||
|
||||
}
|
||||
37
Java/JavaDemo/codedemo/java/lang/reflect/InvokeField.java
Normal file
37
Java/JavaDemo/codedemo/java/lang/reflect/InvokeField.java
Normal file
@@ -0,0 +1,37 @@
|
||||
package cn.aofeng.demo.java.lang.reflect;
|
||||
|
||||
import java.lang.reflect.Field;
|
||||
|
||||
import static cn.aofeng.demo.util.LogUtil.log;
|
||||
|
||||
/**
|
||||
* 通过反射设置字段。
|
||||
*
|
||||
* @author <a href="mailto:aofengblog@163.com">聂勇</a>
|
||||
*/
|
||||
public class InvokeField {
|
||||
|
||||
public static void main(String[] args) throws NoSuchFieldException,
|
||||
SecurityException, IllegalArgumentException, IllegalAccessException {
|
||||
Man man = new Man();
|
||||
Class<?> claz = man.getClass();
|
||||
|
||||
log("==========设置public字段的值==========");
|
||||
log("height的值:%d", man.height);
|
||||
Field field = claz.getField("height");
|
||||
field.setInt(man, 175);
|
||||
log("height的值:%d", man.height);
|
||||
|
||||
log("==========设置private字段的值==========");
|
||||
log("power的值:%d", man.getPower());
|
||||
field = claz.getDeclaredField("power");
|
||||
field.setAccessible(true);
|
||||
field.setInt(man, 100);
|
||||
log("power的值:%d", man.getPower());
|
||||
|
||||
log("==========获取private字段的值==========");
|
||||
int power = field.getInt(man);
|
||||
log("power的值:%d", power);
|
||||
}
|
||||
|
||||
}
|
||||
84
Java/JavaDemo/codedemo/java/lang/reflect/InvokeMethod.java
Normal file
84
Java/JavaDemo/codedemo/java/lang/reflect/InvokeMethod.java
Normal file
@@ -0,0 +1,84 @@
|
||||
package cn.aofeng.demo.java.lang.reflect;
|
||||
|
||||
import java.lang.reflect.InvocationTargetException;
|
||||
import java.lang.reflect.Method;
|
||||
|
||||
import static cn.aofeng.demo.util.LogUtil.log;
|
||||
|
||||
/**
|
||||
* 通过反射调用方法。
|
||||
*
|
||||
* @author <a href="mailto:aofengblog@163.com">聂勇</a>
|
||||
*/
|
||||
public class InvokeMethod {
|
||||
|
||||
/**
|
||||
* 调用父类的方法。
|
||||
*
|
||||
* @param claz
|
||||
* 类
|
||||
* @param man
|
||||
* 类对应的实例
|
||||
*/
|
||||
private static void invokeParentMethod(Class<Man> claz, Man man)
|
||||
throws NoSuchMethodException, IllegalAccessException,
|
||||
InvocationTargetException {
|
||||
// 调用父类的public方法
|
||||
Method method = claz.getMethod("setName", String.class);
|
||||
method.invoke(man, "NieYong");
|
||||
log(man.toString());
|
||||
|
||||
method = claz.getMethod("getName");
|
||||
Object result = method.invoke(man);
|
||||
log("name:%s", result);
|
||||
|
||||
// 调用父类的private方法
|
||||
method = claz.getSuperclass().getDeclaredMethod("reset");
|
||||
method.setAccessible(true);
|
||||
result = method.invoke(man);
|
||||
log(man.toString());
|
||||
}
|
||||
|
||||
/**
|
||||
* 调用自身的方法。
|
||||
*
|
||||
* @param claz
|
||||
* 类
|
||||
* @param man
|
||||
* 类对应的实例
|
||||
*/
|
||||
private static void invokeSelfMethod(Class<Man> claz, Man man)
|
||||
throws NoSuchMethodException, IllegalAccessException,
|
||||
InvocationTargetException {
|
||||
man.setName("XiaoMing");
|
||||
// 调用自身的private方法
|
||||
Method method = claz.getDeclaredMethod("setPower", int.class);
|
||||
method.setAccessible(true);
|
||||
method.invoke(man, 99);
|
||||
log("power:%d", man.getPower());
|
||||
|
||||
// 调用自身的public方法
|
||||
log("%s is marry:%s", man.getName(), (man.isMarry() ? "Yes" : "No"));
|
||||
method = claz.getDeclaredMethod("setMarry", boolean.class);
|
||||
method.invoke(man, true);
|
||||
log("%s is marry:%s", man.getName(), (man.isMarry() ? "Yes" : "No"));
|
||||
|
||||
// 调用静态方法,可将实例设置为null,因为静态方法属于类
|
||||
Man a = new Man("张三");
|
||||
Man b = new Man("李四");
|
||||
method = claz.getMethod("fight", Man.class, Man.class);
|
||||
method.invoke(null, a, b); //
|
||||
}
|
||||
|
||||
public static void main(String[] args) throws NoSuchMethodException,
|
||||
SecurityException, IllegalAccessException,
|
||||
IllegalArgumentException, InvocationTargetException,
|
||||
InstantiationException {
|
||||
Class<Man> claz = Man.class;
|
||||
Man man = claz.newInstance();
|
||||
|
||||
invokeParentMethod(claz, man);
|
||||
invokeSelfMethod(claz, man);
|
||||
}
|
||||
|
||||
}
|
||||
63
Java/JavaDemo/codedemo/java/lang/reflect/Man.java
Normal file
63
Java/JavaDemo/codedemo/java/lang/reflect/Man.java
Normal file
@@ -0,0 +1,63 @@
|
||||
package cn.aofeng.demo.java.lang.reflect;
|
||||
|
||||
import cn.aofeng.demo.json.gson.Person;
|
||||
import cn.aofeng.demo.util.LogUtil;
|
||||
|
||||
/**
|
||||
* 男人。
|
||||
*
|
||||
* @author <a href="mailto:aofengblog@163.com">聂勇</a>
|
||||
*/
|
||||
public class Man extends Person {
|
||||
|
||||
private boolean marry;
|
||||
|
||||
private int power;
|
||||
|
||||
public int height;
|
||||
|
||||
public Man() {
|
||||
super();
|
||||
LogUtil.log("%s的默认构造方法被调用", Man.class.getName());
|
||||
}
|
||||
|
||||
protected Man(String name) {
|
||||
super(name, 0);
|
||||
LogUtil.log("%s带name参数的构造方法被调用", Man.class.getName());
|
||||
}
|
||||
|
||||
@SuppressWarnings("unused")
|
||||
private Man(String name, int age) {
|
||||
super(name, age);
|
||||
LogUtil.log("%s带name和age参数的构造方法被调用", Man.class.getName());
|
||||
}
|
||||
|
||||
public static void fight(Man a, Man b) {
|
||||
String win = "unkown";
|
||||
if (a.power > b.power) {
|
||||
win = a.getName();
|
||||
} else if (b.power > a.power) {
|
||||
win = a.getName();
|
||||
}
|
||||
|
||||
LogUtil.log("%s vs %s, fight result:%s", a.getName(), b.getName(), win);
|
||||
}
|
||||
|
||||
public boolean isMarry() {
|
||||
return marry;
|
||||
}
|
||||
|
||||
public void setMarry(boolean marry) {
|
||||
this.marry = marry;
|
||||
}
|
||||
|
||||
public int getPower() {
|
||||
return power;
|
||||
}
|
||||
|
||||
@SuppressWarnings("unused")
|
||||
private void setPower(int power) {
|
||||
this.power = power;
|
||||
}
|
||||
|
||||
}
|
||||
74
Java/JavaDemo/codedemo/java/lang/serialization/Man.java
Normal file
74
Java/JavaDemo/codedemo/java/lang/serialization/Man.java
Normal file
@@ -0,0 +1,74 @@
|
||||
package cn.aofeng.demo.java.lang.serialization;
|
||||
|
||||
import java.io.Externalizable;
|
||||
import java.io.IOException;
|
||||
import java.io.ObjectInput;
|
||||
import java.io.ObjectOutput;
|
||||
|
||||
/**
|
||||
* 自定义序列化和反序列化。
|
||||
*
|
||||
* @author <a href="mailto:aofengblog@163.com">聂勇</a>
|
||||
*/
|
||||
public class Man implements Externalizable {
|
||||
|
||||
private String manName;
|
||||
|
||||
private int manAge;
|
||||
|
||||
private transient String password;
|
||||
|
||||
public Man() {
|
||||
// nothing
|
||||
}
|
||||
|
||||
public Man(String name, int age) {
|
||||
this.manName = name;
|
||||
this.manAge = age;
|
||||
}
|
||||
|
||||
public Man(String name, int age, String password) {
|
||||
this.manName = name;
|
||||
this.manAge = age;
|
||||
this.password = password;
|
||||
}
|
||||
|
||||
public String getManName() {
|
||||
return manName;
|
||||
}
|
||||
|
||||
public void setManName(String manName) {
|
||||
this.manName = manName;
|
||||
}
|
||||
|
||||
public int getManAge() {
|
||||
return manAge;
|
||||
}
|
||||
|
||||
public void setManAge(int manAge) {
|
||||
this.manAge = manAge;
|
||||
}
|
||||
|
||||
public String getPassword() {
|
||||
return password;
|
||||
}
|
||||
|
||||
public void setPassword(String password) {
|
||||
this.password = password;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void writeExternal(ObjectOutput out) throws IOException {
|
||||
out.writeObject(manName);
|
||||
out.writeInt(manAge);
|
||||
out.writeObject(password);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void readExternal(ObjectInput in) throws IOException, ClassNotFoundException {
|
||||
manName = (String) in.readObject();
|
||||
manAge = in.readInt();
|
||||
password = (String) in.readObject();
|
||||
}
|
||||
|
||||
}
|
||||
79
Java/JavaDemo/codedemo/java/lang/serialization/People.java
Normal file
79
Java/JavaDemo/codedemo/java/lang/serialization/People.java
Normal file
@@ -0,0 +1,79 @@
|
||||
package cn.aofeng.demo.java.lang.serialization;
|
||||
|
||||
import java.io.Serializable;
|
||||
|
||||
/**
|
||||
* 默认序列化和
|
||||
*
|
||||
* @author <a href="mailto:aofengblog@163.com">聂勇</a>
|
||||
*/
|
||||
public class People implements Serializable {
|
||||
|
||||
private static final long serialVersionUID = 6235620243018494633L;
|
||||
|
||||
private String name;
|
||||
|
||||
private int age;
|
||||
|
||||
private transient String address;
|
||||
|
||||
private static String sTestNormal;
|
||||
|
||||
private static transient String sTestTransient;
|
||||
|
||||
public People(String name) {
|
||||
this.name = name;
|
||||
}
|
||||
|
||||
public People(String name, int age) {
|
||||
this.name = name;
|
||||
this.age = age;
|
||||
}
|
||||
|
||||
public People(String name, int age, String address) {
|
||||
this.name = name;
|
||||
this.age = age;
|
||||
this.address = address;
|
||||
}
|
||||
|
||||
public String getName() {
|
||||
return name;
|
||||
}
|
||||
|
||||
public void setName(String name) {
|
||||
this.name = name;
|
||||
}
|
||||
|
||||
public int getAge() {
|
||||
return age;
|
||||
}
|
||||
|
||||
public void setAge(int age) {
|
||||
this.age = age;
|
||||
}
|
||||
|
||||
public String getAddress() {
|
||||
return address;
|
||||
}
|
||||
|
||||
public void setAddress(String address) {
|
||||
this.address = address;
|
||||
}
|
||||
|
||||
public String getsTestNormal() {
|
||||
return sTestNormal;
|
||||
}
|
||||
|
||||
public void setsTestNormal(String sTestNormal) {
|
||||
People.sTestNormal = sTestNormal;
|
||||
}
|
||||
|
||||
public String getsTestTransient() {
|
||||
return sTestTransient;
|
||||
}
|
||||
|
||||
public void setsTestTransient(String sTestTransient) {
|
||||
People.sTestTransient = sTestTransient;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,126 @@
|
||||
package cn.aofeng.demo.java.lang.serialization;
|
||||
|
||||
import java.io.File;
|
||||
import java.io.FileInputStream;
|
||||
import java.io.FileOutputStream;
|
||||
import java.io.IOException;
|
||||
import java.io.ObjectInputStream;
|
||||
import java.io.ObjectOutputStream;
|
||||
|
||||
import org.apache.commons.io.IOUtils;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
/**
|
||||
* 关键字 transient 测试。
|
||||
*
|
||||
* @author <a href="mailto:aofengblog@163.com">聂勇</a>
|
||||
*/
|
||||
public class TransientDemo {
|
||||
|
||||
private static Logger _logger = LoggerFactory.getLogger(TransientDemo.class);
|
||||
|
||||
private String _tempFileName = "TransientDemo";
|
||||
|
||||
/**
|
||||
* 将对象序列化并保存到文件。
|
||||
*
|
||||
* @param obj 待序列化的对象
|
||||
*/
|
||||
public void save(Object obj) {
|
||||
ObjectOutputStream outs = null;
|
||||
try {
|
||||
outs = new ObjectOutputStream(
|
||||
new FileOutputStream( getTempFile(_tempFileName) ));
|
||||
outs.writeObject(obj);
|
||||
} catch (IOException e) {
|
||||
_logger.error("save object to file occurs error", e);
|
||||
} finally {
|
||||
IOUtils.closeQuietly(outs);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 从文件读取内容并反序列化成对象。
|
||||
*
|
||||
* @return {@link People}对象。如果读取文件出错 或 对象类型转换失败,返回null。
|
||||
*/
|
||||
public <T> T load() {
|
||||
ObjectInputStream ins = null;
|
||||
try {
|
||||
ins = new ObjectInputStream(
|
||||
new FileInputStream( getTempFile(_tempFileName)) );
|
||||
return ((T) ins.readObject());
|
||||
} catch (IOException e) {
|
||||
_logger.error("load object from file occurs error", e);
|
||||
} catch (ClassNotFoundException e) {
|
||||
_logger.error("load object from file occurs error", e);
|
||||
} finally {
|
||||
IOUtils.closeQuietly(ins);
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
private File getTempFile(String filename) {
|
||||
return new File(getTempDir(), filename);
|
||||
}
|
||||
|
||||
private String getTempDir() {
|
||||
return System.getProperty("java.io.tmpdir");
|
||||
}
|
||||
|
||||
private void displayPeople(People people) {
|
||||
if (null == people) {
|
||||
return;
|
||||
}
|
||||
String template = "People[name:%s, age:%d, address:%s, sTestNormal:%s, sTestTransient:%s]";
|
||||
System.out.println( String.format(template, people.getName(), people.getAge(),
|
||||
people.getAddress(), people.getsTestNormal(), people.getsTestTransient()));
|
||||
}
|
||||
|
||||
private void displayMan(Man man) {
|
||||
if (null == man) {
|
||||
return;
|
||||
}
|
||||
String template = "Man[manName:%s, manAge:%d, password:%s]";
|
||||
System.out.println( String.format(template, man.getManName(), man.getManAge(), man.getPassword()) );
|
||||
}
|
||||
|
||||
/**
|
||||
* @param args
|
||||
*/
|
||||
public static void main(String[] args) {
|
||||
System.out.println(">>> Serializable测试");
|
||||
TransientDemo demo = new TransientDemo();
|
||||
|
||||
People people = new People("张三", 30, "中国广州");
|
||||
people.setsTestNormal("normal-first");
|
||||
people.setsTestTransient("transient-first");
|
||||
System.out.println("序列化之前的对象信息:");
|
||||
demo.displayPeople(people);
|
||||
demo.save(people);
|
||||
|
||||
// 修改静态变量的值
|
||||
people.setsTestNormal("normal-second");
|
||||
people.setsTestTransient("transient-second");
|
||||
|
||||
People fromLoad = demo.load();
|
||||
System.out.println("反序列化之后的对象信息:");
|
||||
demo.displayPeople(fromLoad);
|
||||
|
||||
|
||||
|
||||
System.out.println("");
|
||||
System.out.println(">>> Externalizable测试");
|
||||
Man man = new Man("李四", 10, "假密码");
|
||||
System.out.println("序列化之前的对象信息:");
|
||||
demo.displayMan(man);
|
||||
demo.save(man);
|
||||
|
||||
Man manFromLoadMan = demo.load();
|
||||
System.out.println("反序列化之后的对象信息:");
|
||||
demo.displayMan(manFromLoadMan);
|
||||
}
|
||||
|
||||
}
|
||||
Reference in New Issue
Block a user