Java创建、删除、授权文件夹和读写文件的方法
bigegpt 2024-10-12 06:12 8 浏览
1. 介绍
1.1 介绍
今天福哥带着大家来学习Java读写文件的方法,虽然现阶段做项目需要用到文件操作的情况不多了,但是免不了在特殊情况下还是需要用到这个技术的。
今天福哥还会给大家讲解Java创建、删除、授权文件夹的方法,这个技术在控制台程序里面用途是非常多的。
Java创建、删除、授权文件夹以及读写文件是依靠File对象来实现的,而读写文件有依赖一些Reader和Writer对象,我们来逐个介绍一下。
文件夹操作就是目录操作,在Windows系统里面文件夹叫folder,翻译过来就是文件夹,在Linux系统里面文件夹叫directory,翻译过来就是目录。所以创建、删除、授权文件夹就是创建、删除、授权目录。
2. 基本原则
读写文件有一些常识需要大家先了解一下。
- 读写文件可以是本地电脑上面的文件,也可以是远程网络上面的文件,只要授权了就可以操作。
- 文件夹操作可以是本地电脑上面的文件夹,也可以是远程网络上面的文件夹,只要授权了就可以操作。
- 要创建文件需要对创建文件的文件夹有写权限。
- 读写已经存在的文件只需要对文件有权限。
- 文件内容分为普通模式和二进制模式,普通模式通过字符串操作,二进制模式通过字节操作。
- 写文件分为重置写入和追加写入,前者会清空已有内容,后者不会。
- 通过文件指针可以精确控制读写文件内容的具体位置,但是写入只会覆盖已有内容而不会像编辑器一样插入内容。
- 当前文件夹通过“.”表示,上一级文件夹通过“..”表示。
- 任何文件夹都会有“当前文件夹”和“上一级文件夹”。
3. 文件夹
3.1 遍历
遍历文件夹用到File对象的listFiles方法,可以通过File对象的isFile方法和isDirectory方法判断文件夹下面的项目是文件还是文件夹,可以通过File对象的canRead判断文件/文件夹是否可读,可以通过File对象的canWrite判断文件/文件夹是否可写。
String currDir = System.getProperty("user.dir");
File dir = new File(currDir);
File[] files = dir.listFiles();
for(int i=0;i<files.length;i++){
String r, w;
r = (files[i].canRead()) ? "可读" : "不可读";
w = (files[i].canWrite()) ? "可写" : "不可写";
if(files[i].isFile()){
out += "文件:[" + r + "][" + w + "]" + files[i].getAbsolutePath() + "<br />";
}
else if(files[i].isDirectory()){
out += "文件夹:[" + r + "][" + w + "]" + files[i].getAbsolutePath() + "<br />";
}
}
3.2 递归遍历
如果需要遍历一个文件夹下面的所有子级文件和文件夹需要用到递归遍历,就是无论是子级还孙级都要遍历出来。
递归遍历很简单,只要在普通遍历的基础之上稍加改动即可实现,首先需要将普通遍历程序封装为一个方法,然后在普通遍历到的项目为文件夹的时候调用一下方法自己,就可以了。
private String listFolder(String currDir){
String out = "";
File dir = new File(currDir);
File[] files = dir.listFiles();
for(int i=0;i<files.length;i++){
String r, w;
r = (files[i].canRead()) ? "可读" : "不可读";
w = (files[i].canWrite()) ? "可写" : "不可写";
if(files[i].isFile()){
out += "文件:[" + r + "][" + w + "]" + files[i].getAbsolutePath() + "<br />";
}
else if(files[i].isDirectory()){
out += "文件夹:[" + r + "][" + w + "]" + files[i].getAbsolutePath() + "<br />";
out = listFolder(files[i].getAbsolutePath());
}
}
return out;
}
@RequestMapping("/net.tongfu.tfjava")
public String response(
){
String out = "";
String currDir = System.getProperty("user.dir");
out += listFolder(currDir);
return out;
}
3.3 创建
创建文件夹使用File的mkdir方法,创建之后可以通过File的setReadable、setWritable、setExecutable方法授权。通过布尔返回值判断创建文件夹是否成功。
String currDir = System.getProperty("user.dir");
String newDir = currDir + "/newDir";
File dir = new File(newDir);
Boolean ret = dir.mkdir();
if(ret){
dir.setReadable(true, false);
dir.setWritable(true, false);
dir.setExecutable(true, false);
}
3.4 删除
删除文件夹使用File的delete方法。
String currDir = System.getProperty("user.dir");
String newDir = currDir + "/newDir";
File dir = new File(newDir);
Boolean ret = dir.delete();
3.5 递归删除
如果文件夹含有子级文件/文件夹则需要先删除子级项目才能删除文件夹,这个时候就需要用到递归遍历技术了。
private void removeFolder(String currDir){
File dir = new File(currDir);
File[] files = dir.listFiles();
for(int i=0;i<files.length;i++){
if(files[i].isFile()){
files[i].delete();
}
else if(files[i].isDirectory()){
removeFolder(files[i].getAbsolutePath());
}
}
dir.delete();
}
@RequestMapping("/net.tongfu.tfjava")
public String response(
){
String out = "";
String currDir = System.getProperty("user.dir");
String newDir = currDir + "/newDir";
removeFolder(newDir);
return out;
}
4. 文件
4.1 创建
Java创建文件可以通过BufferedWriter对象配合FileWriter对象来实现,也可以通过RandomAccessFile对象实现,RandomAccessFile对象更加像PHP的标准方式fopen。
4.1.1 BufferedWriter
使用BufferedWriter创建文件非常容易,虽然不是一行代码可以搞定的(Java似乎很少有一行代码能搞定的事情)。
String currDir = System.getProperty("user.dir");
String newFile = currDir + "/newFile.java";
try {
BufferedWriter file = new BufferedWriter(new FileWriter(newFile));
file.write("这是福哥新创建的文件");
file.close();
}
catch (IOException e){
e.printStackTrace();
}
4.1.2 RandomAccessFile
使用File创建文件需要了解更多知识,首先我们需要指定“文件打开方式”这个概念,使用RandomAccessFile实际上知识打开了一个文件,需要我们指定一个打开文件想要干什么的模式,这个就是文件打开方式。
文件打开方式包括:
- r,读模式
- rw,可读可写模式
- rws,可读可写模式,更新文件内容到设备
- rwd,可读可写模式,更新文件内容到设备
String currDir = System.getProperty("user.dir");
String newFile = currDir + "/newFile.java";
try {
RandomAccessFile file = new RandomAccessFile(newFile, "rw");
file.write((new String("这是福哥新创建的文件")).getBytes());
file.close();
}
catch (FileNotFoundException e){
e.printStackTrace();
}
catch (IOException e){
e.printStackTrace();
}
4.2 删除
删除文件使用File的delete方法。
String currDir = System.getProperty("user.dir");
String newFile = currDir + "/newFile.java";
File file = new File(newFile);
file.delete();
4.3 读文件
读文件就是以读模式或者读写模式打开文件。
4.3.1 BufferedReader
使用BufferedReader读取文件内容并没有非常简便的方法。
String currDir = System.getProperty("user.dir");
String newFile = currDir + "/newFile.java";
try {
BufferedReader file = new BufferedReader(new FileReader(newFile));
String fc = "", line;
while((line = file.readLine()) != null){
fc += line;
}
file.close();
out += fc;
}
catch (FileNotFoundException e){
e.printStackTrace();
}
catch (IOException e){
e.printStackTrace();
}
4.3.2 RandomAccessFile
使用RandomAccessFile读文件和BufferedReader差不多,也是需要用到while语句通过readline循环读取,只不过得到的内容需要自己转换一下编码。
String currDir = System.getProperty("user.dir");
String newFile = currDir + "/newFile.java";
try {
RandomAccessFile file = new RandomAccessFile(newFile, "r");
String fc = "", line;
while((line = file.readLine()) != null){
fc += new String(line.getBytes("8859_1"));
}
file.close();
out += fc;
}
catch (FileNotFoundException e){
e.printStackTrace();
}
catch (IOException e){
e.printStackTrace();
}
4.4 写文件
写文件就是以写模式或者读写模式打开文件。
4.4.1 BufferedWriter
使用BufferedWriter写入内容到文件并没有非常简便的方法。
try {
BufferedWriter fileWriter = new BufferedWriter(new FileWriter(newFile));
BufferedReader fileReader = new BufferedReader(new FileReader(newFile));
fileWriter.write("福哥说这是全部内容了");
fileWriter.close();
String fc = "", line;
while((line = fileReader.readLine()) != null){
fc += line;
}
fileReader.close();
out += fc;
}
catch (FileNotFoundException e){
e.printStackTrace();
}
catch (IOException e){
e.printStackTrace();
}
4.4.2 RandomAccessFile
使用RandomAccessFIle写文件和BufferedWriter差不多,基本上就是从传入字符串改成了传入字节数组。
try {
RandomAccessFile fileWriter = new RandomAccessFile(newFile, "rw");
RandomAccessFile fileReader = new RandomAccessFile(newFile, "r");
fileWriter.write((new String("福哥说这是全部内容了")).getBytes());
fileWriter.close();
String fc = "", line;
while((line = fileReader.readLine()) != null){
fc += new String(line.getBytes("8859_1"));
}
fileReader.close();
out += fc;
}
catch (FileNotFoundException e){
e.printStackTrace();
}
catch (IOException e){
e.printStackTrace();
}
4.5 追加写文件
有时候我们不想将文件内容全部重置了,需要在文件现有内容后面追加内容怎么办?
4.5.1 BufferedWriter
使用BufferedWriter对象比较简单,可以通过构造器的第二个参数来控制是否开启追加模式。
try {
BufferedWriter fileWriter = new BufferedWriter(new FileWriter(newFile, true));
BufferedReader fileReader = new BufferedReader(new FileReader(newFile));
fileWriter.write("福哥又说话了");
fileWriter.close();
String fc = "", line;
while((line = fileReader.readLine()) != null){
fc += line;
}
fileReader.close();
out += fc;
}
catch (FileNotFoundException e){
e.printStackTrace();
}
catch (IOException e){
e.printStackTrace();
}
4.5.2 RandomAccessFile
使用RandomAccessFile对象就是在打开文件后通过seek方法将文件指针移动到文件最后。不知道为什么RandomAccessFile就不设计一个打开方式是追加方式的,真是无语啊~~
try {
RandomAccessFile fileWriter = new RandomAccessFile(newFile, "rw");
RandomAccessFile fileReader = new RandomAccessFile(newFile, "r");
fileWriter.seek(fileWriter.length());
fileWriter.write((new String("福哥又说话了")).getBytes());
String fc = "", line;
while((line = fileReader.readLine()) != null){
fc += new String(line.getBytes("8859_1"));
}
fileReader.close();
out += fc;
}
catch (FileNotFoundException e){
e.printStackTrace();
}
catch (IOException e){
e.printStackTrace();
}
4.6 文件指针
我们以可读可写模式打开文件后,通过seek移动文件指针,在指定位置进行读写操作,这种方式可以避免将文件全部内容加载到内存当中就可以完成很多情况的读写操作,可以解决针对超大文件内容的格式化数据的编辑的难题。
4.6.1 文件数据库
举例:我们制作一个文件数据库,将用户名和密码存储到一个文件里面,用户名和密码格式如下
[用户名(最长50个字符)][密码(取MD5哈希串,所以固定32个字符)][换行]
然后我们只要保证每一组用户信息都是一样的固定长度就可以通过简单计算知道某一个用户ID对应的用户信息在文件的哪个位置上面,进而通过fseek就可以快速定位并读取用户信息了。
因为我们规定了文件内的用户数据格式,那么通过操控文件指针就可以实现这个文本数据库的增、删、改、查功能了,是不是觉得很神奇?
4.6.2 文本数据库定义
福哥在使用RandomAccessFile模拟文本数据库的时候总是有问题,这个等福哥解决了这个问题之后再给大家分享吧~~
4.6.3 文本数据库测试
福哥在使用RandomAccessFile模拟文本数据库的时候总是有问题,这个等福哥解决了这个问题之后再给大家分享吧~~
5. 超大文件读写
超大文件读写需要避免将文件里面的内容全部读出来放到变量里这种行为,因为变量都是存在于内存当中的,如果变量里面的数据太多会把内存用光,就会导致系统瘫痪,这个太可怕了~~
5. 将一个10G文件里的“福哥”换成“鬼谷子叔叔”
这个时候我们可以通过开启两个文件指针,一个文件指针负责读现有文件,一个文件指针负责写新的临时文件,完成后删除现有文件,再将临时文件重命名为原来的文件,就搞定了~~
try{
String currDir = System.getProperty("user.dir");
String newFile = currDir + "/newFile.java";
String tmpFile = currDir + "/newFile.java.tmp";
RandomAccessFile foNew = new RandomAccessFile(newFile, "r");
RandomAccessFile foTmp = new RandomAccessFile(tmpFile, "rw");
if(foNew != null && foTmp != null){
String tmpLine;
while((tmpLine = foNew.readLine()) != null){
tmpLine = new String(tmpLine.getBytes("8859_1"));
tmpLine = tmpLine.replaceAll("福哥", "鬼谷子叔叔");
foTmp.write(tmpLine.getBytes());
}
foNew.close();
foTmp.close();
File fiNew = new File(newFile);
fiNew.delete();
File fiTmp = new File(tmpFile);
fiTmp.renameTo(fiNew);
}
}
catch (IOException e){
e.printStackTrace();
}
总结
好了,今天童鞋们跟着福哥系统地将Java语言操作文件夹、操作文件的方法学习了一遍,有了这些技术之后,今后在项目当中处理各种有关文件夹/文件的问题就不会发怵了!
要注意一点哦,文件夹操作、文件操作属于IO操作,是有一定风险的,一定不要把文件夹/文件的路径搞错了,要不把系统文件或者程序文件写坏了,系统有可能就完蛋了~~
https://m.tongfu.net/home/35/blog/513235.html
- 上一篇:文件读写 文件读写权限在哪里
- 下一篇:Java中一些文件的故事,让我来讲一讲
相关推荐
- Go语言泛型-泛型约束与实践(go1.7泛型)
-
来源:械说在Go语言中,Go泛型-泛型约束与实践部分主要探讨如何定义和使用泛型约束(Constraints),以及如何在实际开发中利用泛型进行更灵活的编程。以下是详细内容:一、什么是泛型约束?**泛型...
- golang总结(golang实战教程)
-
基础部分Go语言有哪些优势?1简单易学:语法简洁,减少了代码的冗余。高效并发:内置强大的goroutine和channel,使并发编程更加高效且易于管理。内存管理:拥有自动垃圾回收机制,减少内...
- Go 官宣:新版 Protobuf API(go pro版本)
-
原文作者:JoeTsai,DamienNeil和HerbieOng原文链接:https://blog.golang.org/a-new-go-api-for-protocol-buffer...
- Golang开发的一些注意事项(一)(golang入门项目)
-
1.channel关闭后读的问题当channel关闭之后再去读取它,虽然不会引发panic,但会直接得到零值,而且ok的值为false。packagemainimport"...
- golang 托盘菜单应用及打开系统默认浏览器
-
之前看到一个应用,用go语言编写,说是某某程序的windows图形化客户端,体验一下发现只是一个托盘,然后托盘菜单的控制面板功能直接打开本地浏览器访问程序启动的webserver网页完成gui相关功...
- golang标准库每日一库之 io/ioutil
-
一、核心函数概览函数作用描述替代方案(Go1.16+)ioutil.ReadFile(filename)一次性读取整个文件内容(返回[]byte)os.ReadFileioutil.WriteFi...
- 文件类型更改器——GoLang 中的 CLI 工具
-
我是如何为一项琐碎的工作任务创建一个简单的工具的,你也可以上周我开始玩GoLang,它是一种由Google制作的类C编译语言,非常轻量和快速,事实上它经常在Techempower的基准测...
- Go (Golang) 中的 Channels 简介(golang channel长度和容量)
-
这篇文章重点介绍Channels(通道)在Go中的工作方式,以及如何在代码中使用它们。在Go中,Channels是一种编程结构,它允许我们在代码的不同部分之间移动数据,通常来自不同的goro...
- Golang引入泛型:Go将Interface「」替换为“Any”
-
现在Go将拥有泛型:Go将Interface{}替换为“Any”,这是一个类型别名:typeany=interface{}这会引入了泛型作好准备,实际上,带有泛型的Go1.18Beta...
- 一文带你看懂Golang最新特性(golang2.0特性)
-
作者:腾讯PCG代码委员会经过十余年的迭代,Go语言逐渐成为云计算时代主流的编程语言。下到云计算基础设施,上到微服务,越来越多的流行产品使用Go语言编写。可见其影响力已经非常强大。一、Go语言发展历史...
- Go 每日一库之 java 转 go 遇到 Apollo?让 agollo 来平滑迁移
-
以下文章来源于GoOfficialBlog,作者GoOfficialBlogIntroductionagollo是Apollo的Golang客户端Apollo(阿波罗)是携程框架部门研...
- Golang使用grpc详解(golang gcc)
-
gRPC是Google开源的一种高性能、跨语言的远程过程调用(RPC)框架,它使用ProtocolBuffers作为序列化工具,支持多种编程语言,如C++,Java,Python,Go等。gR...
- Etcd服务注册与发现封装实现--golang
-
服务注册register.gopackageregisterimport("fmt""time"etcd3"github.com/cor...
- Golang:将日志以Json格式输出到Kafka
-
在上一篇文章中我实现了一个支持Debug、Info、Error等多个级别的日志库,并将日志写到了磁盘文件中,代码比较简单,适合练手。有兴趣的可以通过这个链接前往:https://github.com/...
- 如何从 PHP 过渡到 Golang?(php转golang)
-
我是PHP开发者,转Go两个月了吧,记录一下使用Golang怎么一步步开发新项目。本着有坑填坑,有错改错的宗旨,从零开始,开始学习。因为我司没有专门的Golang大牛,所以我也只能一步步自己去...
- 一周热门
- 最近发表
- 标签列表
-
- mybatiscollection (79)
- mqtt服务器 (88)
- keyerror (78)
- c#map (65)
- xftp6 (83)
- bt搜索 (75)
- c#var (76)
- xcode-select (66)
- mysql授权 (74)
- 下载测试 (70)
- linuxlink (65)
- pythonwget (67)
- androidinclude (65)
- libcrypto.so (74)
- linux安装minio (74)
- ubuntuunzip (67)
- vscode使用技巧 (83)
- secure-file-priv (67)
- vue阻止冒泡 (67)
- jquery跨域 (68)
- php写入文件 (73)
- kafkatools (66)
- mysql导出数据库 (66)
- jquery鼠标移入移出 (71)
- 取小数点后两位的函数 (73)