Java基础—反射

一:反射教程

1.1 反射的定义

动态的获取类的成员变量和方法的机制

1.2 反射的Java demo

ublic class Reflact {
    public static void main(String[] args) throws ClassNotFoundException, NoSuchMethodException, IllegalAccessException, InvocationTargetException, InstantiationException {
        Class clz = Class.forName("com.rent.mp.httpclient.Student");
        Constructor<Student> constructor = clz.getDeclaredConstructor();
        constructor.setAccessible(true);
        Student student = constructor.newInstance();
    }
}

1.3 反射的原理

反射的原理与JVM的类加载过程中的加载机制密切相关

1.3.1 JVM的类加载过程

加载——验证——准备——解析——初始化——使用——销毁
其中第一步加载分为三步:

  1. 根据类的全限定名加载此类的二进制字节流
  2. 将二进制字节流对应的静态数据区域转换为方法区的运行时数据结构
  3. 在内存中生成此类的一个Class对象,作为方法区此类各种数据的访问入口

1.3.2 反射的原理

注意上述的第三步,每个类都会生成一个且只生成一个Class对象,所以程序运行时直接加载此Class对象即可获取数据。

1.4 动态代理

1.5

二:IO

2.1 IO概述

IO代表输入输出流:身处二进制的世界,IO流可分为字节流和字符流也可按输入输出分为输入/输出流。
InputStream/OutputStream:字节流
Reader/Writer:字符流
InputStreamReader:是一种字符流,用于将字节流转换为字符流

			需要转换—— 转换流 InputStreamReader 、OutputStreamWriter
			需要高效—— 缓冲流Bufferedxxx
			多个源—— 序列流 SequenceInputStream
		   对象序列化—— ObjectInputStream、ObjectOutputStream
		   保证数据的输出形式—— 打印流PrintStream 、Printwriter
		   操作基本数据,保证字节原样性——DataOutputStream、DataInputStream

2.2 IO

输入:即将硬盘/网络中的数据加载到内存
输出:将内存中的数据写入到硬盘等

2.3 File

代表着一个文件(包括文件/文件夹),
1.1 File概述
java.io.File 类是专门对文件进行操作的类,只能对文件本身进行操作,不能对文件内容进行操作。
java.io.File 类是文件和目录路径名的抽象表示,主要用于文件和目录的创建、查找和删除等操作。

怎么理解上面两句话?其实很简单!

第一句就是说File跟流无关,File类不能对文件进行读和写也就是输入和输出!
第二句就是说File主要表示类似D:\文件目录1与D:\文件目录1\文件.txt,前者是文件夹(Directory)后者则是文件(file),而File类就是操作这两者的类。

1.2 构造方法
在java中,一切皆是对象,File类也不例外,不论是哪个对象都应该从该对象的构造说起,所以博主来分析分析File类的构造方法。首先从API开始着手
在这里插入图片描述
我们主要来学习一下比较常用的三个:

1、 public File(String pathname) :通过将给定的路径名字符串转换为抽象路径名来创建新的 File实例。
2、 public File(String parent, String child) :从父路径名字符串和子路径名字符串创建新的 File实例。
3、 public File(File parent, String child) :从父抽象路径名和子路径名字符串创建新的 File实例。

看字描述不够生动不够形象不得劲?没得事,下面进行构造举例,马上就生动形象了,代码如下:

  1. 一个File对象代表硬盘中实际存在的一个文件或者目录。
  2. File类构造方法不会给你检验这个文件或文件夹是否真实存在,因此无论该路径下是否存在文件或者目录,都不影响File对象的创建。
    // 文件路径名
    String path = “D:\123.txt”;
    File file1 = new File(path);

// 文件路径名
String path2 = “D:\1\2.txt”;
File file2 = new File(path2); -------------相当于D:\1\2.txt

// 通过父路径和子路径字符串
String parent = “F:\aaa”;
String child = “bbb.txt”;
File file3 = new File(parent, child); --------相当于F:\aaa\bbb.txt

// 通过父级File对象和子路径字符串
File parentDir = new File(“F:\aaa”);
String child = “bbb.txt”;
File file4 = new File(parentDir, child); --------相当于F:\aaa\bbb.txt
File类的注意点:

一个File对象代表硬盘中实际存在的一个文件或者目录。
File类构造方法不会给你检验这个文件或文件夹是否真实存在,因此无论该路径下是否存在文件或者目录,都不影响File对象的创建。
1.3 常用方法
File的常用方法主要分为获取功能、获取绝对路径和相对路径、判断功能、创建删除功能的方法

1.3.1 获取功能的方法
1、public String getAbsolutePath() :返回此File的绝对路径名字符串。

2、public String getPath() :将此File转换为路径名字符串。

3、public String getName() :返回由此File表示的文件或目录的名称。

4、public long length() :返回由此File表示的文件的长度。

以上方法测试,代码如下【注意测试以自己的电脑文件夹为准】:

public class FileGet {
public static void main(String[] args) {
File f = new File(“d:/aaa/bbb.java”);
System.out.println(“文件绝对路径:”+f.getAbsolutePath());
System.out.println(“文件构造路径:”+f.getPath());
System.out.println(“文件名称:”+f.getName());
System.out.println(“文件长度:”+f.length()+“字节”);

    File f2 = new File("d:/aaa");     
    System.out.println("目录绝对路径:"+f2.getAbsolutePath());
    System.out.println("目录构造路径:"+f2.getPath());
    System.out.println("目录名称:"+f2.getName());
    System.out.println("目录长度:"+f2.length());
}

}
输出结果:
文件绝对路径:d:\aaa\bbb.java
文件构造路径:d:\aaa\bbb.java
文件名称:bbb.java
文件长度:2116字节

目录绝对路径:d:\aaa
目录构造路径:d:\aaa
目录名称:aaa
目录长度:3236
注意:length(),表示文件的长度。但是File对象表示目录,则返回值未指定。

1.3.2 绝对路径和相对路径
绝对路径:一个完整的路径,以盘符开头,例如F://aaa.txt。
相对路径:一个简化的路径,不以盘符开头,例如//aaa.txt//b.txt。

1、路径是不区分大小写
2、路径中的文件名称分隔符windows使用反斜杠,反斜杠是转义字符,两个反斜杠代表一个普通的反斜杠

//绝对路径
public class FilePath {
public static void main(String[] args) {
// D盘下的bbb.java文件
File f = new File(“D:\bbb.java”);
System.out.println(f.getAbsolutePath());

    // 项目下的bbb.java文件
    File f2 = new File("bbb.java");
    System.out.println(f2.getAbsolutePath());
}

}
输出结果:
D:\bbb.java
D:\java\bbb.java
1.3.3判断功能的方法
1、 public boolean exists() :此File表示的文件或目录是否实际存在。
2、 public boolean isDirectory() :此File表示的是否为目录。
3、public boolean isFile() :此File表示的是否为文件。

方法演示,代码如下:

public class FileIs {
public static void main(String[] args) {
File f = new File(“d:\aaa\bbb.java”);
File f2 = new File(“d:\aaa”);
// 判断是否存在
System.out.println(“d:\aaa\bbb.java 是否存在:”+f.exists());
System.out.println(“d:\aaa 是否存在:”+f2.exists());
// 判断是文件还是目录
System.out.println(“d:\aaa 文件?:”+f2.isFile());
System.out.println(“d:\aaa 目录?:”+f2.isDirectory());
}
}
输出结果:
d:\aaa\bbb.java 是否存在:true
d:\aaa 是否存在:true
d:\aaa 文件?:false
d:\aaa 目录?:true
1.3.4 创建删除功能的方法
public boolean createNewFile() :文件不存在,创建一个新的空文件并返回true,文件存在,不创建文件并返回false。
public boolean delete() :删除由此File表示的文件或目录。
public boolean mkdir() :创建由此File表示的目录。
public boolean mkdirs() :创建由此File表示的目录,包括任何必需但不存在的父目录。
其中,mkdirs()和mkdir()方法类似,但mkdir(),只能创建一级目录,mkdirs()可以创建多级目录比如//a//b//c,所以开发中一般用mkdirs();

这些方法中值得注意的是createNewFile方法以及mkdir与mkdirs的区别

方法测试,代码如下:

public class FileCreateDelete {
public static void main(String[] args) throws IOException {
// 文件的创建
File f = new File(“aaa.txt”);
System.out.println(“是否存在:”+f.exists()); // false
System.out.println(“是否创建:”+f.createNewFile()); // true
System.out.println(“是否创建:”+f.createNewFile()); // 以及创建过了所以再使用createNewFile返回false
System.out.println(“是否存在:”+f.exists()); // true

    // 目录的创建
    File f2= new File("newDir");    
    System.out.println("是否存在:"+f2.exists());// false
    System.out.println("是否创建:"+f2.mkdir()); // true
    System.out.println("是否存在:"+f2.exists());// true

    // 创建多级目录
    File f3= new File("newDira\\newDirb");
    System.out.println(f3.mkdir());// false
    File f4= new File("newDira\\newDirb");
    System.out.println(f4.mkdirs());// true
  
    // 文件的删除
    System.out.println(f.delete());// true
  
    // 目录的删除
    System.out.println(f2.delete());// true
    System.out.println(f4.delete());// false
}

}
注意:delete方法,如果此File表示目录,则目录必须为空才能删除。

1.4 目录的遍历
public String[] list() :返回一个String数组,表示该File目录中的所有子文件或目录。

public File[] listFiles() :返回一个File数组,表示该File目录中的所有的子文件或目录。

public class FileFor {
public static void main(String[] args) {
File dir = new File(“G:\光标”);

    //获取当前目录下的文件以及文件夹的名称。
    String[] names = dir.list();
    for(String name : names){
        System.out.println(name);
    }
    //获取当前目录下的文件以及文件夹对象,只要拿到了文件对象,那么就可以获取更多信息
    File[] files = dir.listFiles();
    for (File file : files) {
        System.out.println(file);
    }
}

}
在这里插入图片描述
listFiles在获取指定目录下的文件或者文件夹时必须满足下面两个条件

1,指定的目录必须存在

2,指定的必须是目录。否则容易引发返回数组为null,出现NullPointerException异常

1.5 递归遍历文件夹下所有文件以及子文件
不说啥了,直接上代码:

package File;

import java.io.File;

//递归遍历文件夹下所有的文件
public class RecursionDirectory {
public static void main(String[] args) {
File file=new File(“D:\java专属IO测试”);
Recursion(file);
}
public static void Recursion(File file){
//1、判断传入的是否是目录
if(!file.isDirectory()){
//不是目录直接退出
return;
}
//已经确保了传入的file是目录
File[] files = file.listFiles();
//遍历files
for (File f: files) {
//如果该目录下文件还是个文件夹就再进行递归遍历其子目录
if(f.isDirectory()){
//递归
Recursion(f);
}else {
//如果该目录下文件是个文件,则打印对应的名字
System.out.println(f.getName());
}

    }
}

}

2.4 Files

是java提供的用于操作Files的工具类,主要有创建目录,创建文件,复制文件等操作。

2.5 Paths

是Path的工具类

2.4 IO demo

// zip文件的解压
public class Zip {
    private static Logger zLogger = Logger.getLogger("main.java.Zip");
    public static void unZip(File srcFile, String destDirPath) throws IOException {
        // 1.判断文件是否存在 或是否为zip文件
        if (Objects.isNull(srcFile) || !srcFile.exists() || !srcFile.getName().endsWith(".zip")) {
            zLogger.warning(String.format("解压失败:可能原因 1.不存在源文件 2.路径无效 path:%s 3.文件非zip文件 %s", srcFile, srcFile.getName().endsWith(".zip")));
            throw new FileNotFoundException(String.format("不存在源文件,或路径无效。path:%s", srcFile));
        }
        // 2.参数准备
        if (Objects.isNull(destDirPath) || destDirPath.equals("")) {
            destDirPath = srcFile.getParent();
        }
        // 得到解压路径
        Path destPath = Paths.get(destDirPath, String.valueOf(File.separatorChar) + srcFile.getName().substring(0, srcFile.getName().lastIndexOf(".")));
        Files.deleteIfExists(destPath);
        // 3.进行解压 不易解压大文件
        ZipFile zFile = new ZipFile(srcFile, Charset.forName("gbk"));
        Enumeration<? extends ZipEntry> zEntries = zFile.entries();
        ZipEntry zipEntry = null;
        while (zEntries.hasMoreElements()) {
            zipEntry = zEntries.nextElement();
            zipEntry.getName();
            if (!zipEntry.isDirectory()) {
                InputStreamReader inputStreamReader = new InputStreamReader(zFile.getInputStream(zipEntry), new GBK());
                Path destFilePath = Paths.get(destPath.toString() + (File.separatorChar) + zipEntry.getName());
                Files.deleteIfExists(destFilePath);
                if (!Files.exists(destFilePath.getParent())) {
                    Files.createDirectories(destFilePath.getParent());
                }
                Files.createFile(destFilePath);
                File destFile = destFilePath.toFile();
                Writer writer = new FileWriter(destFile);
                StringBuffer content = new StringBuffer();
                int n = 0;
                char[] chars = new char[1024];
                while (true) {
                    n = inputStreamReader.read(chars);
                    System.out.println((chars));
                    content.append(chars);
                    chars = new char[1024];
                    if (n == -1) {
                        inputStreamReader.close();
                        break;
                    }
                }
                writer.write(content.toString());
                writer.close();
            } else {
                Files.createDirectories(Paths.get(destPath.normalize().toString() + File.separator + zipEntry.getName()));
            }
        }
    }
}

三:反射和IO面试题

https://www.cnblogs.com/Java-JJ/p/12690779.html
https://www.cnblogs.com/linanana/p/12545947.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值