黑马程序员技术交流社区

标题: 【阳哥专栏】技术分活动第13期 [打印本页]

作者: 王震阳老师    时间: 2014-8-23 10:40
标题: 【阳哥专栏】技术分活动第13期
本帖最后由 就业指导-王震阳老师 于 2014-8-24 12:18 编辑

声明:以后的技术分活动中的技术题,越来越偏向于数据结构、算法、JVM、多线程、高并发等,因此对于基础的要求也是更高的。
活动目的:练习javaSE知识。

活动奖励:最高3个技术分

结束时间:2014年8月29日,过期提交可能获取不到技术分!

代码提交要求:将自己的源代码压缩然后提交,提交的时候设置为管理员权限,以其他方式提交的答案无效。上交源码的时候不需要将整个工程项目压缩,只需将用到的源文件压缩即可。

题目类型:JavaSE 自定义类加载器。

难易程度:较难

题目:老规矩,回帖领题


往期技术分题:【阳哥专栏】技术分活动第14期
http://bbs.itheima.com/thread-139429-1-1.html
【阳哥专栏】技术分活动第12期
http://bbs.itheima.com/thread-138162-1-1.html
【阳哥专栏】技术分活动第11期
http://bbs.itheima.com/thread-137632-1-1.html
【阳哥专栏】技术分活动第10期
http://bbs.itheima.com/thread-136866-1-1.html
【阳哥专栏】技术分活动第9期
http://bbs.itheima.com/thread-136465-1-1.html
【阳哥专栏】技术分活动第8期
http://bbs.itheima.com/thread-135781-1-1.html
【阳哥专栏】技术分活动第7期
http://bbs.itheima.com/thread-134321-1-1.html
【阳哥专栏】周末技术分活动第6期
http://bbs.itheima.com/thread-132893-1-1.html
【阳哥专栏】周末技术分活动第5期
http://bbs.itheima.com/thread-129859-1-1.html
【阳哥专栏】周末技术分活动第4期
http://bbs.itheima.com/thread-128854-1-1.html
【阳哥专栏】周末技术分活动第3期
http://bbs.itheima.com/thread-127326-1-1.html
【阳哥专栏】周末技术分活动第2期
http://bbs.itheima.com/thread-125800-1-1.html
【阳哥专栏】周末技术分派送活动第1期
http://bbs.itheima.com/thread-123979-1-1.html











作者: java_dream    时间: 2014-8-23 11:07
我又来领题了
作者: justin1258    时间: 2014-8-23 11:30
没抢到沙发。。。。
作者: 唕    时间: 2014-8-23 11:44
看看题:sleepy:
作者: ddewym123    时间: 2014-8-23 11:44
本帖最后由 ddewym123 于 2014-8-24 21:02 编辑

请查收!

MyClassLoader.rar

1.38 KB, 阅读权限: 200, 下载次数: 1


作者: weity    时间: 2014-8-23 11:59
看看~~拿题领分
作者: justin1258    时间: 2014-8-23 12:11
交题喽~~

MyClassLoaderDemo.zip

1018 Bytes, 阅读权限: 200, 下载次数: 1


作者: 迷失的独白    时间: 2014-8-23 12:16
本帖最后由 迷失的独白 于 2014-8-25 18:35 编辑

羊哥请查收!!!

ClassLoaderTest.rar

1.32 KB, 阅读权限: 200, 下载次数: 1


作者: 李彦来    时间: 2014-8-23 12:28
看一下下
作者: 潘多拉    时间: 2014-8-23 13:23
领题喽领题喽,滔哥万岁,滔哥一生幸福
作者: nadax    时间: 2014-8-23 14:04
我是来领题的
作者: yqj    时间: 2014-8-23 14:38
看看题!
作者: 赵连明    时间: 2014-8-23 14:42
看看来拿分了
作者: wenjd0000    时间: 2014-8-23 14:52
看下题目能做不
作者: 孙小亚    时间: 2014-8-23 19:35
阳哥真赞!!
作者: Baiye    时间: 2014-8-23 19:40
先拿题 看看
作者: java_dream    时间: 2014-8-23 19:44
交题啦!

test.rar

2.23 KB, 阅读权限: 200, 下载次数: 1

自定义类加载器


作者: 朱冰18189949658    时间: 2014-8-23 19:59
第三次领题了
作者: yqj    时间: 2014-8-23 20:04
做完了,交题!

ClassLoaderTest.zip

1.27 KB, 阅读权限: 200, 下载次数: 1


作者: lhtwm1    时间: 2014-8-23 21:03
那初学者不是 完蛋了
作者: SmallRooker    时间: 2014-8-23 21:21
本帖最后由 SmallRooker 于 2014-8-25 22:18 编辑

老师交题,虽然有些不明白 ,还有一些是抄袭了本吧里的代码。写好几遍了。已经记住原理了,现在正在刻苦学习这方面知识!加油!

cn.test.rar

7.02 KB, 阅读权限: 150, 下载次数: 2


作者: 孙小亚    时间: 2014-8-23 21:24
来提交啦!我是写了三个java文件,放在一个文件夹里面,阳哥辛苦了。。。
代码 测试结果.zip (6.41 KB, 下载次数: 1)
作者: tonglingwang    时间: 2014-8-23 21:38
阳哥,来领题
作者: 姠佐メ亾佑つ    时间: 2014-8-23 21:46
看看 什么题目

作者: ︶ㄣ你眼中的倒    时间: 2014-8-23 21:59
顶!!!!!!!!!!!!!
作者: MeryStyle    时间: 2014-8-23 22:55
板凳,领题~!
作者: 赵连明    时间: 2014-8-23 23:05

做这个把自己反射的思路都理清了

1111111.zip

1.68 KB, 阅读权限: 200, 下载次数: 1


作者: huangxuanheng    时间: 2014-8-23 23:24
挑战来了
作者: 八零、玖羚    时间: 2014-8-23 23:29
回帖拿题,哈哈
作者: 刘亚东    时间: 2014-8-24 01:21
回帖领题
作者: 依然超级赛亚人    时间: 2014-8-24 07:01
最好了准备,领一份题。
作者: 冒牌高手    时间: 2014-8-24 07:18
明知道自己不会也得看看题
作者: 龙飞九天    时间: 2014-8-24 08:17
来看看,领题
作者: cat73    时间: 2014-8-24 09:30
看看题目 这次不要在错过了!!!!!!!!!!
作者: 萍水相逢    时间: 2014-8-24 09:31
看一下!
作者: 画了一个圈儿    时间: 2014-8-24 10:34
回帖 求题
作者: Wokno    时间: 2014-8-24 11:08
看看。。。。。。。。。。。
作者: 喜爱    时间: 2014-8-24 11:10
嘻嘻。。。。。来领了哦!
作者: Wokno    时间: 2014-8-24 11:13
请查收!

itheima.classloader.zip

6.04 KB, 阅读权限: 200, 下载次数: 1


作者: cat73    时间: 2014-8-24 12:37
本帖最后由 cat73 于 2014-8-27 22:58 编辑

不知道这个可以不- -

test.zip (11.93 KB, 下载次数: 1)

以上文件使用自定义的类加载器实现了加载经过Base64编码后的类

并且附带了编译一个类并Base64编码的代码
需要在eclipse导入才能正常的进行编译(主要是文件名的问题...)

作者: vodart    时间: 2014-8-24 15:30
第一次领题。
作者: 3040789425    时间: 2014-8-24 18:09
看题                              
作者: Justfeeling    时间: 2014-8-24 18:26
只为头排,努力抢沙发!
作者: bbdeyouxang    时间: 2014-8-25 10:21
回帖取题
作者: 菜鸟一号    时间: 2014-8-25 13:43
回复看看题目
作者: 我要淡定。    时间: 2014-8-25 18:19
赞一个!
作者: 小乖乖灬浩歌    时间: 2014-8-25 22:31
这2期的技术分活动相距很近哦
作者: 黑马黄武先    时间: 2014-8-26 09:14
有这活动真好
作者: 丸子    时间: 2014-8-27 09:46
领题了。。。。
作者: 正在请求链接    时间: 2014-8-27 11:52
没沙发,板凳好硬
作者: 旭辉lin    时间: 2014-8-27 21:12
我来领题了。
作者: 小乖乖灬浩歌    时间: 2014-8-27 21:57
不得不说  做这个题目之前 我听都没有听说过ClassLoader   建议阳阳哥每次当期技术分活动结束以后  放开相应附件的下载权限 这样大家可以观摩学习下

src.zip

2.75 KB, 阅读权限: 200, 下载次数: 1

ClassLoader技术分


作者: 八零、玖羚    时间: 2014-8-28 00:48
学完,敲完,递交完,洗洗睡了

MyClassLoader.rar

1.54 KB, 阅读权限: 200, 下载次数: 1

类加载器、反射


作者: 逸晨    时间: 2014-8-28 10:20
领题看看。
作者: 王震阳老师    时间: 2014-8-28 13:30
孙小亚 发表于 2014-8-23 21:24
来提交啦!我是写了三个java文件,放在一个文件夹里面,阳哥辛苦了。。。
...

可以:
  1. package com.itheima.loadertest;
  2. /**
  3. * 自定义一个类加载器,并且通过该类加载器加载一个类源码,并且运行改类中的一个方法。
  4. * @author Sunzy
  5. *
  6. */
  7. import java.io.*;

  8. public class MyClassLoader extends ClassLoader{
  9.         private String name;
  10.         // 通过这个构造方法生成的类加载器,它的父加载器是系统类加载器  
  11.     public MyClassLoader(String name) {  
  12.         super();
  13.         this.name = name;  
  14.     }
  15.     // 通过这个这个构造方法生成的类加载器,该加载器的父加载器是loader,如果为空,则父加载器为根加载器
  16.     public MyClassLoader(String name, ClassLoader loader) {  
  17.         super(loader);   
  18.         this.name = name;  
  19.     }
  20.     // 要重写findclass这个方法
  21.     @Override
  22.         protected Class<?> findClass(String name) throws ClassNotFoundException {
  23.             byte[] data = null;  
  24.         FileInputStream fis = null;  
  25.        try {  
  26.            fis = new FileInputStream("E:\\workspace_Android\\DailyTest1\\bin\\com\\itheima\\loadertest\\"+name+".class");  
  27.        } catch (FileNotFoundException e) {  
  28.            System.out.println(e);  
  29.        }  
  30.         ByteArrayOutputStream abos = new ByteArrayOutputStream();  
  31.         int ch = 0;  
  32.         try {  
  33.            while ((ch=fis.read()) != -1)  {  
  34.                  abos.write(ch);        //把字节一个一个写到输出流中  
  35.             }  
  36.        } catch (IOException e) {  
  37.            e.printStackTrace();  
  38.        }  
  39.         data = abos.toByteArray();   //把输出流中的字节弄成一个字节数组  
  40.        return this.defineClass("com.itheima.loadertest."+name,data, 0, data.length,null);  
  41.     }                
  42.        
  43.         public String toString()  
  44.     {  
  45.         return this.name;  
  46.     }  
  47.    
  48. }
复制代码

作者: 王震阳老师    时间: 2014-8-28 13:31
SmallRooker 发表于 2014-8-23 21:21
老师交题,虽然有些不明白 ,还有一些是抄袭了本吧里的代码。写好几遍了。已经记住原理了,现在正在刻苦学 ...

能学到东西就行,不过你怎么把文件解压的代码提交了,这个模块提交的自定义类加载器呀?
作者: 王震阳老师    时间: 2014-8-28 13:33
ddewym123 发表于 2014-8-23 11:44
请查收!

挺好:
  1. package com.cn.brainfreeze;

  2. import java.io.BufferedInputStream;
  3. import java.io.ByteArrayOutputStream;
  4. import java.io.FileInputStream;
  5. import java.io.FileNotFoundException;
  6. import java.io.IOException;
  7. import java.lang.reflect.Method;

  8. //自定义类加载器
  9. public class MyClassLoader extends ClassLoader{
  10.         //定义两个成员变量,表示类加载器的名字与欲加载类的父路径
  11.         private String name;
  12.         private String path;
  13.        
  14.         //让系统类加载器成为该类加载器的父级类加载器
  15.         public MyClassLoader(String name) {
  16.                 super();
  17.                 this.name=name;
  18.         }
  19.         //让给定的类加载器成为该类加载器的父级类加载器
  20.         public MyClassLoader(ClassLoader parent,String name) {
  21.                 super(parent);
  22.                 this.name=name;
  23.         }
  24.        
  25.         //name与path的getter与setter方法
  26.         public String getName() {
  27.                 return name;
  28.         }
  29.         public void setName(String name) {
  30.                 this.name = name;
  31.         }
  32.         public String getPath() {
  33.                 return path;
  34.         }
  35.         public void setPath(String path) {
  36.                 this.path = path;
  37.         }
  38.        
  39.         //重写findClass方法,使其加载指定目录的class文件
  40.         @Override
  41.         @SuppressWarnings("deprecation")
  42.         protected Class<?> findClass(String name) throws ClassNotFoundException {
  43.                 byte[] data=loadClassData(name);
  44.                 return defineClass(data, 0, data.length);
  45.         }
  46.        
  47.         //将class文件转化为byte[]
  48.         private byte[] loadClassData(String name) {
  49.                 //获取被加载类的完整路径
  50.                 String fileName=name.replace('.', '/');
  51.                 String filePath=path+fileName+".class";
  52.                
  53.                 /*通过BufferedInputStream读取目标class文件,
  54.                  * ByteArrayOutputStream将读取的文件转化为byte[]
  55.                  */
  56.                 BufferedInputStream in=null;
  57.                 ByteArrayOutputStream out=null;
  58.                 byte[] data=null;
  59.                 try {
  60.                         in=new BufferedInputStream(new FileInputStream(filePath));
  61.                         out=new ByteArrayOutputStream();
  62.                         byte[] buf=new byte[1024];
  63.                         int len=0;
  64.                         while ((len=in.read(buf))!=-1) {
  65.                                 out.write(buf,0,len);               
  66.                         }
  67.                         data=out.toByteArray();                       
  68.                 } catch (FileNotFoundException e) {
  69.                         e.printStackTrace();
  70.                 } catch (IOException e) {
  71.                         e.printStackTrace();
  72.                 }finally{ //关闭流
  73.                         if(in!=null)
  74.                                 try {
  75.                                         in.close();
  76.                                 } catch (IOException e) {
  77.                                         e.printStackTrace();
  78.                                 }finally{
  79.                                         if(out!=null)
  80.                                                 try {
  81.                                                         out.close();
  82.                                                 } catch (IOException e) {
  83.                                                         e.printStackTrace();
  84.                                                 }
  85.                                 }
  86.                 }
  87.                 return data;
  88.         }
  89.        
  90.         //重写toString方法
  91.         @Override
  92.         public String toString() {
  93.                 return this.name;
  94.         }
  95.        
  96.         //测试
  97.         public static void main(String[] args) throws Exception{
  98.                 MyClassLoader mcl=new MyClassLoader("myClassLoader");
  99.                 mcl.setPath("d:/");
  100.                 Class clazz=mcl.loadClass("com.cn.brainfreeze.Simple");
  101.                 Object simple=clazz.newInstance();
  102.                 Method function=clazz.getMethod("function");       
  103.                 function.invoke(simple);
  104.         }
  105. }
复制代码

作者: 王震阳老师    时间: 2014-8-28 13:34
迷失的独白 发表于 2014-8-23 12:16
羊哥请查收!!!

可以:
  1. package com.itheima;

  2. import java.io.BufferedInputStream;
  3. import java.io.ByteArrayOutputStream;
  4. import java.io.File;
  5. import java.io.FileInputStream;
  6. import java.io.IOException;
  7. import java.io.InputStream;

  8. public class ClassLoaderTest {       

  9.         public static void main(String[] args)throws Exception {
  10.                 String loadDir = "";//可以加载其他文件夹的类文件,但下边的代码需要修改,且只能执行类文件的父类的方法
  11.                 String loadClazz = "com.itheima.ClassLoaderAttachment";
  12.                 Class clazz = new MyClassLoader(loadDir).loadClass(loadClazz);               
  13.                 ClassLoaderAttachment cla = (ClassLoaderAttachment)clazz.newInstance().getClass().getConstructor().newInstance();
  14.                 System.out.println(cla.toString());
  15.                 cla.fun();
  16.         }
  17. }

  18. class MyClassLoader extends ClassLoader{       

  19.     private String loadDir;  
  20.     private final String fileType = ".class";

  21.         public MyClassLoader() {
  22.         }
  23.        
  24.         public MyClassLoader(String loadDir) {
  25.                 this.loadDir = loadDir;
  26.         }
  27.        
  28.         protected Class<?> findClass(String name) {
  29.                         byte[] bytes = this.loadClassData(name);
  30.                         return defineClass(null, bytes, 0, bytes.length);
  31.         }       
  32.                
  33.         private byte[] loadClassData(String name) {  
  34.         InputStream in = null;  
  35.         byte[] data = null;  
  36.         ByteArrayOutputStream baos = null;  
  37.   
  38.         try {  
  39.             name = name.replace(".", "\\");  
  40.             in = new BufferedInputStream(new FileInputStream(new File(loadDir + name + fileType)));  
  41.             baos = new ByteArrayOutputStream();  
  42.             int ch = 0;  
  43.             while (-1 != (ch = in.read())) {  
  44.                 baos.write(ch);  
  45.             }  
  46.             data = baos.toByteArray();  
  47.         } catch (Exception e) {  
  48.   
  49.             e.printStackTrace();  
  50.         } finally {  
  51.             try {  
  52.                 in.close();  
  53.             } catch (IOException e1) {  
  54.                 e1.printStackTrace();  
  55.             } finally {  
  56.                 try {  
  57.                     baos.close();  
  58.                 } catch (IOException e2) {  
  59.                     e2.printStackTrace();  
  60.                 }  
  61.             }  
  62.         }  
  63.         return data;  
  64.     }

  65. }
复制代码

作者: 王震阳老师    时间: 2014-8-28 13:35
java_dream 发表于 2014-8-23 19:44
交题啦!

good:
  1. package test;

  2. import java.io.File;
  3. import java.io.FileInputStream;
  4. import java.io.IOException;
  5. import java.lang.reflect.Method;

  6. public class CompileClassLoader extends ClassLoader{
  7.         //读取一个文件的内容(即Class文件,如Hello.class)
  8.         private byte[] getBytes(String filename) throws IOException{
  9.                 File file = new File(filename);
  10.                 long len = file.length();
  11.                 byte[] raw = new byte[(int)len];
  12.                 FileInputStream fis = null;
  13.                 try{
  14.                         fis = new FileInputStream(file);
  15.                         //一次读取Class文件的全部二进制数据
  16.                         int r = fis.read(raw);
  17.                         if(r != len)
  18.                                 throw new IOException("无法读取全部文件:"+r+"!="+len);
  19.                         return raw;
  20.                 }catch(IOException ioe){
  21.                         throw new RuntimeException("读取文件失败!");
  22.                 }finally{
  23.                         try{
  24.                                 if(fis != null)
  25.                                         fis.close();
  26.                         }catch(IOException ioe){
  27.                                 throw new RuntimeException("读取流关闭失败!");
  28.                         }
  29.                 }
  30.         }
  31.        
  32.         //定义编译指定Java源文件的方法
  33.         private boolean compile(String javaFilename) throws IOException{
  34.                 System.out.println("CompileClassLoader:正在编译"+javaFilename+"...");
  35.                 //调用系统的Javac命令
  36.                 Process p = Runtime.getRuntime().exec("javac "+javaFilename);
  37.                 try{
  38.                         //其它线程都等待这个线程完成
  39.                         p.waitFor();
  40.                 }catch(InterruptedException ie){
  41.                         ie.printStackTrace();
  42.                 }
  43.                 //获取javac线程的退出值
  44.                 int ret = p.exitValue();
  45.                 //返回编译是否成功
  46.                 return ret == 0;
  47.         }
  48.        
  49.         //重写ClassLoader的findClass方法
  50.         protected Class<?> findClass(String name) throws ClassNotFoundException{
  51.                 Class clazz = null;
  52.                 //将包路径中的点(.)替换成斜线(/)
  53.                 String fileStub = name.replace(".", "/");
  54.                 String javaFilename = fileStub+".java";
  55.                 String classFilename = fileStub+".class";
  56.                 File javaFile = new File(javaFilename);
  57.                 File classFile = new File(classFilename);
  58.                
  59.                 //当指定Java源文件存在,且Class文件不存在,
  60.                 //或者java源文件的修改时间比Class文件的修改时间更晚,重新编译
  61.                 if(javaFile.exists() &&(!classFile.exists() || javaFile.lastModified()>classFile.lastModified())){
  62.                         try{
  63.                                 //如果编译失败,或者该Class文件不存在
  64.                                 if(!compile(javaFilename) || !classFile.exists()){
  65.                                         throw new ClassNotFoundException("=============ClassNotFoundException:"+javaFilename);
  66.                                 }
  67.                         }catch(IOException ioe){
  68.                                 ioe.printStackTrace();
  69.                         }
  70.                 }
  71.                 //如果Class文件存在,系统负责将该文件转化成Class对象
  72.                 if(classFile.exists()){
  73.                         try{
  74.                                 //将class文件的二进制数据读入数组
  75.                                 byte[] raw = getBytes(classFilename);
  76.                                 //调用ClassLoader的defineClass方法将二进制数据转换成Class对象
  77.                                 clazz = defineClass(name, raw, 0, raw.length);
  78.                         }catch(IOException ioe){
  79.                                 ioe.printStackTrace();
  80.                         }
  81.                 }
  82.                 //如果clazz为null,表名加载失败,则抛出异常
  83.                 if(clazz == null){
  84.                         throw new ClassNotFoundException(name);
  85.                 }
  86.                 return clazz;
  87.         }
  88.        
  89.         //定义主方法
  90.         public static void main(String[] args) throws Exception{
  91.                 //如果运行该程序(自定义类加载器CompileClassLoader)时没有参数,即没有目标类
  92.                 if(args.length<1){
  93.                         System.out.println("缺少目标类,请按如下格式运行Java源文件:");
  94.                         System.out.println("java CompileClassLoader ClassName");
  95.                         return;
  96.                 }
  97.                 //第一个参数是需要运行的类
  98.                 String progClass = args[0];
  99.                 //剩下的参数将作为运行目标类是的参数
  100.                 //将这些参数复制到一个新数组中
  101.                 String[] progArgs = new String[args.length-1];
  102.                 System.arraycopy(args, 1, progArgs, 0, progArgs.length);
  103.                 CompileClassLoader ccl = new CompileClassLoader();
  104.                 //加载需要运行的类
  105.                 Class<?> clazz = ccl.loadClass(progClass);
  106.                 //获取需要运行的类的主方法
  107.                 Method main = clazz.getMethod("main", (new String[0]).getClass());
  108.                 Object[] argsArray = {progArgs};
  109.                 main.invoke(null, argsArray);
  110.         }
  111. }
复制代码

作者: 王震阳老师    时间: 2014-8-28 13:36
yqj 发表于 2014-8-23 20:04
做完了,交题!

很好:
  1. package cn.test;

  2. import java.io.ByteArrayOutputStream;
  3. import java.io.File;
  4. import java.io.FileInputStream;
  5. import java.io.InputStream;
  6. import java.lang.reflect.Constructor;
  7. import java.lang.reflect.Method;
  8. /*
  9. * 为了方便将所有的类写在了个java文件中
  10. * MyClassLoader为自定义的ClassLoader
  11. * TestClass为用来测试类
  12. * ClassLoaderTest为测试类
  13. */

  14. /**
  15. * 自定义的ClassLoader
  16. */
  17. class MyClassLoader extends ClassLoader {
  18.         private String rootDir;

  19.         public MyClassLoader(String rootDir) {
  20.                 this.rootDir = rootDir;
  21.         }

  22.         @Override
  23.         protected Class<?> findClass(String name) throws ClassNotFoundException {
  24.                 byte[] b = getClassData(name);
  25.                 return defineClass(name, b, 0, b.length);
  26.         }
  27.        
  28.         // 读取class字节码为byte数组
  29.         private byte[] getClassData(String name) {
  30.                 if (name == null) {
  31.                         return null;
  32.                 } else {
  33.                         //将name中的"."替换为"/"
  34.                         name = name.replace(".", "/");
  35.                         name=name+".class";
  36.                         try {//将类的class文件读取为byte数组
  37.                                 InputStream in = new FileInputStream(new File(new File(rootDir), name));
  38.                                 ByteArrayOutputStream out = new ByteArrayOutputStream();
  39.                                
  40.                                 byte[] b = new byte[1024];
  41.                                 int len = 0;
  42.                                 while ((len = in.read(b)) != -1) {
  43.                                         out.write(b, 0, len);
  44.                                 }
  45.                                 return out.toByteArray();
  46.                                
  47.                         } catch (Exception e) {
  48.                                 throw new RuntimeException("读取class文件失败!");
  49.                         }
  50.                 }
  51.         }
  52. }

  53. /**
  54. * 用来测试的类
  55. */
  56. class TestClass{
  57.         private void say() {
  58.                 System.out.println("hello world!");
  59.         }
  60. }
  61. /**
  62. *
  63. *测试用自定义的ClassLoad读取TestClass类并运行say()方法
  64. *需要用到反射技术
  65. */
  66. public class ClassLoaderTest {
  67.         public static void main(String[] args) throws Exception {
  68.                 //获取当前类的父地址,由于Class.getResource("")获取的是一个URL,需要切除"file:/"前缀
  69.                 String rootDir=ClassLoaderTest.class.getClassLoader().getResource("").toString();
  70.                 rootDir=rootDir.substring("file:/".length());
  71. //                System.out.println(rootDir);
  72.                 //用自定义的ClassLoad读取TestClass类
  73.                 MyClassLoader classLoader=new MyClassLoader(rootDir);
  74.                 Class<?> clazz=classLoader.findClass("cn.test.TestClass");
  75.                
  76.                 //实例化clazz
  77.                 Constructor<?> c=clazz.getDeclaredConstructor();
  78.                 if(!c.isAccessible()){//暴力反射
  79.                         c.setAccessible(true);
  80.                 }
  81.                 Object o=c.newInstance();
  82.                 //获取clazz的say()方法,并执行
  83.                 Method sayMethod=clazz.getDeclaredMethod("say");
  84.                 if(!sayMethod.isAccessible()){//暴力反射
  85.                         sayMethod.setAccessible(true);
  86.                 }
  87.                 sayMethod.invoke(o);        //打印成功:hello world!
  88.         }
  89. }
复制代码

作者: ximi    时间: 2014-8-28 14:02
领题了,谢谢了
作者: ximi    时间: 2014-8-28 16:35
阳哥,文件已经已经提交,辛苦啦:D

ClassLoaderTest.zip

1.53 KB, 阅读权限: 200, 下载次数: 1


作者: 旭辉lin    时间: 2014-8-28 20:39
请查收!

Test3.zip

9.63 KB, 阅读权限: 200, 下载次数: 3


作者: 王震阳老师    时间: 2014-8-28 20:57
旭辉lin 发表于 2014-8-28 20:39
请查收!

挺好:
  1. package classload;

  2. /**
  3. * @author:
  4. * @date:
  5. * @description:自定义ClassLoader
  6. */
  7. import java.io.File;
  8. import java.io.FileInputStream;
  9. import java.io.FileNotFoundException;
  10. import java.io.IOException;
  11. import java.lang.reflect.InvocationTargetException;
  12. import java.lang.reflect.Method;

  13. public class CompileClassLoader extends ClassLoader {
  14.         // 读入源文件转换为字节数组
  15.         private byte[] getSource(String filename) {
  16.                 File file = new File(filename);
  17.                 int length = (int) file.length();
  18.                 byte[] contents = new byte[length];
  19.                 FileInputStream fis = null;
  20.                 try {
  21.                         fis = new FileInputStream(file);
  22.                         int r = fis.read(contents);
  23.                         if (r != length) {
  24.                                 throw new IOException("IOException:无法读取" + filename);
  25.                         }
  26.                 } catch (FileNotFoundException e) {
  27.                         e.printStackTrace();
  28.                 } catch (IOException e) {
  29.                         e.printStackTrace();
  30.                 } finally {
  31.                         try {
  32.                                 if (fis != null) {
  33.                                         fis.close();
  34.                                 }
  35.                         } catch (IOException e) {
  36.                                 e.printStackTrace();
  37.                         }
  38.                 }
  39.                 return contents;
  40.         }

  41.         // 编译文件
  42.         public boolean compile(String javaFile) {
  43.                 System.out.println("正在编译" + javaFile);
  44.                 int ret = 0;
  45.                 try {
  46.                         // 调用系统命令编译文件
  47.                         Process process = Runtime.getRuntime().exec("javac " + javaFile);
  48.                         process.waitFor();
  49.                         ret = process.exitValue();
  50.                 } catch (IOException e) {
  51.                         e.printStackTrace();
  52.                 } catch (InterruptedException e) {
  53.                         e.printStackTrace();
  54.                 }
  55.                 return ret == 0;
  56.         }

  57.         // 重写findclass
  58.         @Override
  59.         protected Class<?> findClass(String name) throws ClassNotFoundException {
  60.                 Class<?> clazz = null;
  61.                 // 将文件的.替换为/,例如com.lyl.reflect.Reflect被替换为com/lyl/reflect/Reflect
  62.                 String fileStub = name.replace(".", "/");
  63.                 // java源文件名
  64.                 String javaFileName = fileStub + ".java";
  65.                 // 编译后的class文件名
  66.                 String classFileName = fileStub + ".class";
  67.                 File javaFile = new File(javaFileName);
  68.                 File classFile = new File(classFileName);
  69.                 // 当指定JAVA源文件存在,且class文件不存在,
  70.                 // 或者java源文件的修改时间比class文件修改时间晚则重新编译
  71.                 if (javaFile.exists()
  72.                                 && (!classFile.exists() || javaFile.lastModified() > classFile
  73.                                                 .lastModified())) {
  74.                         // 如果编译失败,或者class文件不存在
  75.                         if (!compile(javaFileName) || !classFile.exists()) {
  76.                                 throw new ClassNotFoundException("ClassNotFoundException:"
  77.                                                 + javaFileName);
  78.                         }
  79.                 }
  80.                 // 如果CLASS文件按存在,系统负责将该文件转换成Class对象
  81.                 if (classFile.exists()) {
  82.                         byte[] raw = getSource(classFileName);
  83.                         // 将ClassLoader的defineClass方法将二进制数据转换成Class对象
  84.                         int divindex = name.indexOf("\\");
  85.                         String javafilename = null;
  86.                         // 如果是某个盘里面的文件,要去掉文件的盘符
  87.                         if (divindex != -1) {
  88.                                 javafilename = name.substring(divindex + 1, name.length());
  89.                         }
  90.                         // 将字节数组转换为class实例
  91.                         clazz = defineClass(javafilename, raw, 0, raw.length);
  92.                 }
  93.                 // 如果clazz为null,表明加载失败,则抛出异常
  94.                 if (clazz == null) {
  95.                         throw new ClassNotFoundException(name);
  96.                 }
  97.                 return clazz;
  98.         }

  99.         // 定义主方法
  100.         public static void main(String[] args) throws ClassNotFoundException,
  101.                         SecurityException, NoSuchMethodException, IllegalArgumentException,
  102.                         IllegalAccessException, InvocationTargetException {
  103.                 // 如果运行该程序没有参数,则没有目标类
  104.                 if (args.length < 1) {
  105.                         System.out.println("缺少运行的目标类,请按如下格式运行源文件");
  106.                         System.out.println("java CompileClassLoader ClassName");
  107.                         System.exit(0);
  108.                 }
  109.                 // 第一个参数为需要运行的类
  110.                 String proClass = args[0];
  111.                 // 剩下的参数将作为目标类得参数
  112.                 String[] proArgs = new String[args.length - 1];
  113.                 System.arraycopy(args, 1, proArgs, 0, proArgs.length);
  114.                 CompileClassLoader ccl = new CompileClassLoader();
  115.                 // 加载需要运行的类
  116.                 Class<?> clazz = ccl.loadClass(proClass);
  117.                 Method main = clazz.getMethod("main", (new String[0]).getClass());
  118.                 Object[] argsArray = { proArgs };
  119.                 main.invoke(null, argsArray);
  120.         }
  121. }
复制代码

作者: Fengs    时间: 2014-8-29 01:56
恩恩额!
作者: ql627666537    时间: 2014-8-29 13:34
回复回复 领提领题

作者: yingsun    时间: 2014-8-30 21:37
有分送啦!
作者: fantacyleo    时间: 2014-9-1 01:04
虽然错过了,还是看看题目吧
作者: lvc    时间: 2014-9-1 03:50
看看。。。
作者: quq947115876    时间: 2014-9-1 21:27
领题看看
作者: yingsun    时间: 2014-9-2 02:56
看看学习一下。
作者: Faith_Yee    时间: 2014-9-9 10:59
回帖领题~!
作者: 21Guns。    时间: 2014-9-10 03:10
吊啊.  我也想看看题...
作者: 好听就好    时间: 2014-9-13 22:46
看看以前的题目,感受下
作者: 一苇芦江    时间: 2014-9-17 10:23
新手来领题了
作者: daoqin    时间: 2014-9-17 12:12
刚学了这个,来试试
作者: daoqin    时间: 2014-9-17 12:19
做完了,请查收

ClassLoad.rar

1.16 KB, 阅读权限: 150, 下载次数: 1


作者: 就是现在    时间: 2014-9-18 14:17
求技术分
作者: 就是现在    时间: 2014-9-18 19:32
   黑马程序员训练营的入学这么严格, 难怪黑马程序员训练营敢喊不1万就业不给学费的口号,敢先培训后付款。容易得来的东西不懂得珍惜!

src.rar

1.68 KB, 阅读权限: 200, 下载次数: 1

求技术分


作者: Huberry    时间: 2014-9-20 02:27
回帖领题
作者: chensc    时间: 2014-9-21 12:18
学习学习!
作者: 追逐我的明天    时间: 2014-9-21 21:29
领题来了
作者: 炎星辰    时间: 2014-9-23 18:57
哇塞
                           
作者: 炎星辰    时间: 2014-9-23 18:58
看看题目                                                     

作者: chensc    时间: 2014-9-23 19:54
学习学习!
作者: 遮天    时间: 2014-9-25 18:38
看下题目.........
作者: 油油油菜花    时间: 2014-10-9 10:56
加油!!
作者: sugar    时间: 2014-10-12 21:02
来领题目啦
作者: palex    时间: 2014-11-11 03:24
看看题目
作者: ttbx_刘    时间: 2014-11-20 03:19
领题!领题!领题!!!
作者: 木乃伊    时间: 2014-12-11 09:05
好变态,才刚刚开始学啊,前面的题目都不会:lol
作者: 祁祯祥    时间: 2014-12-14 19:23
回帖领题13
作者: 王震阳老师    时间: 2014-12-15 12:03
木乃伊 发表于 2014-12-11 09:05
好变态,才刚刚开始学啊,前面的题目都不会

加油。
作者: lby369    时间: 2014-12-18 18:30
领题来了,看看这个会不会简单点儿
作者: 风祭将o    时间: 2014-12-28 09:03
这个知识点比较模糊
作者: Eagle    时间: 2015-1-4 13:45
类加载器是反射部分的,应该可以做
作者: gxb2459    时间: 2015-1-9 20:21
回帖领题
作者: sjzxst2    时间: 2015-1-9 23:16
看看较难的题啥样!
作者: zhouli_2014    时间: 2015-1-13 08:43
领以前的题
作者: gxb2459    时间: 2015-1-17 23:17
回帖领题




欢迎光临 黑马程序员技术交流社区 (http://bbs.itheima.com/) 黑马程序员IT技术论坛 X3.2