请稍等 ...
×

采纳答案成功!

向帮助你的同学说点啥吧!感谢那些助人为乐的人

如果不用jar包运行,程序应该怎么写呢?

我直接运行Application.Main 函数,走断点调试,发现请求

失败,原因是代码中写的是必须以jar包的形式运行,我想知道,如果不以jar包的形式运行,代码应该怎么写呢?

正在回答 回答被采纳积分+3

2回答

时光1124 2019-08-26 17:30:04
package core;

import java.io.File;
import java.io.FileFilter;
import java.io.IOException;
import java.net.JarURLConnection;
import java.net.URL;
import java.net.URLDecoder;
import java.util.ArrayList;
import java.util.Enumeration;
import java.util.List;
import java.util.Set;
import java.util.jar.JarEntry;
import java.util.jar.JarFile;

/**
 * @Author : L_C
 * @Date Created in 9:28 2019/8/26
 * @Description :
 * @Modified :
 */
public class ClassScanner {
    public static List<Class<?>> classes = new ArrayList<>();
    public static List<Class<?>> scanClasses(String packageName) throws IOException, ClassNotFoundException {
        List<Class<?>> classList = new ArrayList<>();
        String path = packageName.replace(".","/");
        ClassLoader classLoader = Thread.currentThread().getContextClassLoader();
        Enumeration<URL> resources = classLoader.getResources(path);
        while (resources.hasMoreElements()){
            URL resource = resources.nextElement();
            if(resource.getProtocol().contains("jar")){
                JarURLConnection jarURLConnection = (JarURLConnection)resource.openConnection();
                String jarFilePath = jarURLConnection.getJarFile().getName();
                classList.addAll(getClassesFromJar(jarFilePath,path));
            }else{
                String filePath = URLDecoder.decode(resource.getPath(), "UTF-8");
                System.out.println(filePath);
                // 是否循环迭代
                boolean recursive = true;
                classList.addAll(  findAndAddClassesInPackageByFile(packageName, filePath, recursive));
            }
        }
        return classList;
    }

    private static List<Class<?>> getClassesFromJar(String jarFilePath,String path) throws IOException, ClassNotFoundException {
        JarFile jarFile = new JarFile(jarFilePath);
        Enumeration<JarEntry> jarEntries = jarFile.entries();
        while (jarEntries.hasMoreElements()){
            JarEntry jarEntry = jarEntries.nextElement();
            String entryName = jarEntry.getName();//com.top.test.Test.class
            if (entryName.startsWith(path)&&entryName.endsWith(".class")){
                String classFullName = entryName.replace("/",".").substring
                        (0,entryName.length()-6);
                classes.add(Class.forName(classFullName));
            }
        }
        return classes;
    }
    /**
     * 以文件的形式来获取包下的所有Class
     *
     * @param packageName
     * @param packagePath
     * @param recursive
     */
    public static List<Class<?>> findAndAddClassesInPackageByFile(String packageName, String packagePath, final boolean recursive ) {

        // 获取此包的目录 建立一个File
        File dir = new File(packagePath);
        // 如果不存在或者 也不是目录就直接返回
        if (!dir.exists() || !dir.isDirectory()) {
            // log.warn("用户定义包名 " + packageName + " 下没有任何文件");
            return null;
        }
        // 如果存在 就获取包下的所有文件 包括目录
        File[] dirfiles = dir.listFiles(new FileFilter() {
            // 自定义过滤规则 如果可以循环(包含子目录) 或则是以.class结尾的文件(编译好的java类文件)
            public boolean accept(File file) {
                return (recursive && file.isDirectory()) || (file.getName().endsWith(".class"));
            }
        });
        // 循环所有文件
        for (File file : dirfiles) {
            // 如果是目录 则继续扫描
            if (file.isDirectory()) {
                findAndAddClassesInPackageByFile(packageName + "." + file.getName(), file.getAbsolutePath(), recursive);
            } else {
                // 如果是java类文件 去掉后面的.class 只留下类名
                String className = file.getName().substring(0, file.getName().length() - 6);
                try {
                    // 添加到集合中去
                    // classes.add(Class.forName(packageName + '.' +
                    // className));
                    // 经过回复同学的提醒,这里用forName有一些不好,会触发static方法,没有使用classLoader的load干净
                    classes.add(
                            Thread.currentThread().getContextClassLoader().loadClass(packageName + '.' + className));
                } catch (ClassNotFoundException e) {
                    // log.error("添加用户自定义视图类错误 找不到此类的.class文件");
                    e.printStackTrace();
                }
            }
        }
        return classes;
    }
}


1 回复 有任何疑惑可以回复我~
  • 提问者 zzylove #1
    代码中运行的条件还是以jar包运行吧?我问的是如果不以jar包的形式,怎么运行,还是我没看懂这个代码。
    回复 有任何疑惑可以回复我~ 2019-08-27 11:26:12
  • 时光1124 回复 提问者 zzylove #2
    用我贴的代码 把课程里的代码替换掉 就可以直接在Application.Main里启动了啊
    回复 有任何疑惑可以回复我~ 2019-09-19 09:37:43
soberyang 2019-08-27 00:30:50

我这个应该比较简单

if (resource.getProtocol().contains("jar")){
   URLConnection urlConnection = resource.openConnection();
   JarURLConnection jarURLConnection = (JarURLConnection)urlConnection;
   JarFile jarFile = jarURLConnection.getJarFile();
   String jarFilePath= jarFile.getName();
   classList.addAll(getClassFromJar(jarFilePath, path));
}else{
   //todo
   List<File> files = new ArrayList<>(16);
   File file = new File(resource.getPath());
   files.add(file);
   while (files.size()!=0){
       File scanFile = files.remove(0);
       if (scanFile.isDirectory()){
           List<File> listTmp = Arrays.asList(scanFile.listFiles());
           files.addAll(listTmp);
       }else {
           String fullFileName = scanFile.getAbsolutePath();
           if (fullFileName.endsWith(".class")){
               String fullClassName = fullFileName.replace(File.separator, ".").substring(0, fullFileName.length() - 6);
               String[] split = fullClassName.split(packageName);
               String classRealName = split[split.length-1];
               System.out.println("全路径名:"+classRealName);
               classList.add(Class.forName(packageName + classRealName));
           }
       }
   }
}

0 回复 有任何疑惑可以回复我~
问题已解决,确定采纳
还有疑问,暂不采纳
意见反馈 帮助中心 APP下载
官方微信