(一)File類
使用一個類描述文件與文件夾---File類
File類的構造函數
File(String pathname) 指定文件或文件夾的路徑,創建一個File對象
File(File parent,String child) 指定父路徑與子路徑構建一個File對象,應用場景:有時需要父路徑先做預處理,然後才能處理子文件
File(String parent,String child)
public class iostream_demo1 {
public static void main(String[] args) {
File parentFile=new File("E:\\");//父路徑,
File file=new File(parentFile,"a.txt");//子路徑
//File file=new File("E:\\a.txt");//創建一個File對象
System.out.println("文件存在麼?"+file.exists());
}
}
目錄分隔符:在Windows中分隔符爲'\',在Unix/Linux中分隔符爲'/'。
java程序跨平臺。
注意:
1.在Windows操作系統下,可以使用\與/作爲目錄分隔符,但是在Unix/Linux操作系統下,只能使用/作爲目錄分隔符。
路徑:
絕對路徑:指定文件的完整路徑創建一個File對象,絕對路徑一般以盤符開頭。
相對路徑:資源文件相對於當前路徑。
. 代表是當前路徑
.. 代表是上一級路徑
注意:如果當前路徑與資源文件不在同一個盤符下,無法寫相對路徑。
public class iostream_demo2 {
public static void main(String[] args) {
/*
File file=new File("E:\\a.txt");//因爲\轉義,所以要出現\,必須用\\
File file1=new File("E:/a.txt");
System.out.println("文件存在麼?"+file.exists());
System.out.println("文件存在麼?"+file1.exists());
System.out.println("目錄分隔符:"+file.separator);// Windows下是\
*/
File file1=new File(".");
System.out.println("當前絕對路徑:"+file1.getAbsolutePath());//C:\Users\lenovo\eclipse-workspace\day19\. 程序當前在day19文件夾下
File file=new File("..\\..\\eclipse");//..找到day19,..找到eclipse-workspace,與eclipse在同一個路徑下
System.out.println("文件存在麼?"+file.exists());
File file2=new File("src\test.txt");
System.out.println("文件存在麼?"+file2.exists());//當前路徑下的文件夾中的文件
}
}
通過File類常用的方法可以獲取以及修改文件的屬性數據。
創建:
createNewFile() 在指定位置創建一個空文件,成功返回true,若已存在則不創建並返回false
mkdir() 在指定位置創建目錄,這隻會創建最後一級目錄,若上級目錄不存在即拋出異常。
mkdirs() 在指定位置創建目錄,會創建路徑中所有不存在的目錄
renameTo(File dest) 重命名文件或文件夾,也可以操作非空的文件夾。
public class iostream_demo3 {
public static void main(String[] args)throws IOException {
File file=new File("E:\\bb");
File dir=new File("E:\\aa\\bb");
System.out.println("創建一個空文件:"+file.createNewFile());//拋出io異常,防止硬盤壞掉,無法創建
System.out.println("創建一個文件夾:"+dir.mkdirs());//不能以後綴名判斷是文件還是文件夾
File destfile=new File("F:\\aa");
file.renameTo(destfile);
/*
如果源文件與目標文件在同一級路徑下,那麼renameTo是重命名,若不在同一級目錄下,那麼renameTo是剪切。
若源文件夾與目標文件夾在同一級路徑下,那麼renameTo是重命名,若不在同一級目錄下,那麼renameTo不起作用。
*
* */
}
}
刪除:
delete (立即)刪除文件或一個空文件夾,如果是文件夾且不爲空,則不能刪除。
deleteOnExit 虛擬機終止時,請求刪除此抽象路徑名錶示的文件或目錄,保證程序異常時創建的臨時文件也可以被刪除
判斷:
exists() 文件或文件夾是否存在
isFile() 是否是一個文件
isDirectory() 是否一個目錄(文件夾)
isHidden() 是否隱藏的文件或文件夾
isAbsolute() 測試此抽象路徑名是否爲絕對路徑名
public class iostream_demo4 {
public static void main(String[] args) {
File file=new File("..\\..\\a.txt");
System.out.println("文件存在麼?"+file.exists());
System.out.println("是一個文件麼?"+file.isFile());
System.out.println("是一個文件夾麼?"+file.isDirectory());
System.out.println("是否隱藏文件:"+file.isHidden());
System.out.println("是否絕對路徑名:"+file.isAbsolute());
//System.out.println("刪除成功麼?"+file.delete());
}
}
獲取:
getName() 獲取文件或文件夾的名稱,不包含上級路徑
getPath() 返回絕對路徑,可以是相對路徑,但是目錄要指定
getAbsolutePath() 獲取文件的絕對路徑,與文件是否存在無關(不具體指定是當前路徑)
length() 獲取文件的大小(字節數) ,文件不存在返回0L,文件夾也返回0L
getParent() 返回此抽象路徑名父目錄的路徑名字符串,若此路徑名沒有指定目錄,返回null
lastModified() 獲取最後一次修改的時間,返回的是從1970.1.0起的毫秒值,可以轉換成格式日期
public class iostream_demo5 {
public static void main(String[] args) {
File file=new File("E:\\abc.txt");
System.out.println("文件名:"+file.getName());
System.out.println("路徑名:"+file.getPath());
System.out.println("絕對路徑名:"+file.getAbsolutePath());
System.out.println("文件大小:"+file.length());
System.out.println("父路徑:"+file.getParent());
long time=file.lastModified();
Date date=new Date(time);
//日期格式化類
SimpleDateFormat dateFormat=new SimpleDateFormat("yyyy年MM月dd日 HH:mm:ss");
System.out.println("最後一次修改的時間:"+dateFormat.format(date));
}
}
文件夾相關:
static File[] listRoots() 列出所有的根目錄(Windows中就是所有系統的盤符)
list 返回路徑下的子文件名和子文件夾名
listFiles 返回路徑下的子文件和子文件夾對象
public class iostream_demo6 {
public static void main(String[] args) {
/*
File[] files=File.listRoots();//列出所有盤符
for(File file:files) {
System.out.println(file);
}*/
File file=new File("E:\\BaiduNetdiskDownload");
/*
String[] fileNames=file.list();//不包括孫文件
for(String fileName:fileNames) {
System.out.println(fileName);
}*/
File[] files=file.listFiles();//把所有子文件和子目錄存儲到File數組中返回
for(File file1:files) {
System.out.println(file1);//返回子文件對象
}
}
}
練習:
需求1:定義一個函數列出指定目錄中所有的java文件。
需求2:列出指定目錄中的所有子文件名與子目錄名,要求目錄名與文件名分開列出。
public class iostream_test1 {
public static void main(String[] args) {
File file=new File("E:\\test");
javaFiles(file);
filesName(file);
}
public static void javaFiles(File file) {
File[] files=file.listFiles();
for(File file1:files) {
String name=file1.getName();
/*
if(name.endsWith(".java")) {//字符串是否以.java結束
System.out.println(file1);
}*/
if(name.matches(".+\\.java")) {//正則表達式匹配(文件的名字是任意的字符所以是.,+表示有多個字符,\\.匹配.,後面是java)
System.out.println(name);//文件名與正則相匹配
}
}
}
public static void filesName(File file) {
File[] files=file.listFiles();
/*
ArrayList<String> fileList=new ArrayList<String>();
ArrayList<String> direList=new ArrayList<String>();
for(File file1:files) {
if(file1.isFile()) {
fileList.add(file1.getName());
}else if(file1.isDirectory()){
direList.add(file1.getName());
}
}
System.out.println("文件是:");
Iterator it1=fileList.iterator();
while(it1.hasNext()) {
System.out.println(it1.next());
}
System.out.println("目錄是:");
Iterator it2=direList.iterator();
while(it2.hasNext()) {
System.out.println(it2.next());
}
*/
//或者不用集合,直接遍歷兩次
System.out.println("文件是:");
for(File file1:files) {
if(file1.isFile()) {
System.out.println("\t"+file1.getName());
}
}
System.out.println("目錄是:");
for(File file1:files) {
if(file1.isDirectory()) {
System.out.println("\t"+file1.getName());
}
}
}
}
(二)FileInputStream讀取數據文件
File類 僅能獲取文件的屬性數據或修改文件的屬性數據,不能讀取文件的內容。
如果需要操作文件內容數據,就需要學習"IO流"技術。
IO流類別:
1.流向劃分:
輸入流
輸出流
輸入流、輸出流的判斷標準:
以當前程序作爲參照物,數據如果流出,使用輸出流,若數據流入則使用輸入流。
2.處理的單位:
字節流:字節流用於讀取文件的字節數據,讀取到的數據不會經過任何處理。
字符流:讀取到的字節數據會轉換成看得懂的字符數據,讀取的是以字符爲單位的數據。字符流=字節流+解碼。
輸入字節流:
InputStream 抽象類 輸入字節流的基類。
FileInputStream 讀取文件數據的字節流
使用FileInputStream 讀取文件數據:
1.找到目標文件
2.建立數據的輸入通道
3.讀取文件數據
public class input_demo1 {
public static void main(String[] args) throws IOException {
read4();
}
//方式1:無法完整讀取一個文件的數據
public static void read1()throws IOException {//ctrl-t可以看到異常的整個繼承體系
//第一步:找到目標文件對象
File file=new File("E:abc.txt");
//第二步:建立數據的輸入通道
FileInputStream fileInputStream=new FileInputStream(file);
//第三步:讀取文件數據
int content=fileInputStream.read();//返回的是讀取的字節數據,每次只會讀取一個字節
System.out.println("讀到的內容:"+(char)content);
//第四步:關閉資源(釋放資源文件)
fileInputStream.close();
}
//方式2:每次讀取一個字節的數據,可以讀取完整文件的數據。
public static void read2() throws IOException{
//第一步:找到目標文件對象
File file=new File("E:abc.txt");
//第二步:建立數據通道
FileInputStream fileInputStream=new FileInputStream(file);
//第三步:讀取文件數據
int content=0;
while((content=fileInputStream.read())!=-1) {//read方法若讀到文件末尾則返回-1表示
System.out.print((char)content);
}
//關閉資源
fileInputStream.close();
}
//方式3:使用(緩衝數組)字節數據讀取
public static void read3() throws IOException{
//找到目標文件
File file=new File("E:\\abc.txt");
//建立數據通道
FileInputStream fileInputStream=new FileInputStream(file);
//創建一個字節數組,讀取文件數據
byte[] buf=new byte[1024];//(理論上)緩衝字節數組,一般越大,效率越高
int length=fileInputStream.read(buf);//read方法接收一個字節數組read(byte[] buf),將讀取到的內容保存到數組中,返回的是本次讀取到的字節數。
System.out.println("字節數:"+length);
System.out.println("讀取到的內容是:"+new String(buf,0,length));//用讀取到的字節組成一個字符串
fileInputStream.close();
}
//方式4:使用循環配合緩衝數組(分次讀取),可以讀取完整文件
public static void read4() throws IOException{
//找到目標文件
File file=new File("E:\\abc.txt");
//建立數據通道
FileInputStream fileInputStream=new FileInputStream(file);
//讀取文件數據
byte[] buf=new byte[12];//緩衝數組
int length=0;//記錄本次讀取的字節個數
while((length=fileInputStream.read(buf))!=-1) {
//System.out.println("length:"+length);
System.out.println(new String(buf,0,length));
}
//關閉資源
fileInputStream.close();
}
}
(三)FileOutputStream寫數據
輸出字節流:
OutputStream 抽象類,所有輸出字節流的父類。
FileOutputStream 向文件輸出數據的輸出字節流。
使用FileOutputStream的步驟:
1.找到目標文件
2.建議數據的輸出通道
3.把數據寫出
4.關閉資源
FileOutputStream要注意的細節:
1.new FileOutputStream時,如果目標文件不存在,會先創建目標文件,再寫入。
2.new FileOutputStream時,如果目標文件已存在,會先清空目標文件的數據,再寫入新的數據。
3.寫入數據時如果需要以追加形式寫入,需要使用new FileOutputStream(file,true)構造函數。
4.使用write(int b)方法的時候,雖然參數接受的一個int類型的數據,但是實際上只會把數據的低八位寫出,其他24位丟掉。
public class output_demo1 {
public static void main(String[] args) throws IOException{
write3();
}
//方式1:每次只能寫一個字節數據
public static void write1()throws IOException {
//找到目標文件
File file=new File("E:\\abc.txt");
//建立數據的輸出通道
FileOutputStream fileOutputStream=new FileOutputStream(file);
//把數據寫出
fileOutputStream.write('h');
fileOutputStream.write('e');
fileOutputStream.write('l');
fileOutputStream.write('l');
fileOutputStream.write('o');
//關閉資源
fileOutputStream.close();
}
//方式2:把數據轉成字節數組然後寫出。
public static void write2()throws IOException{
//找到目標文件
File file=new File("E:\\aaa.txt");
//建立數據的輸出通道
FileOutputStream fileOutputStream=new FileOutputStream(file,true);//第二個參數爲true時,寫入文件時以追加形式寫入
//準備數據,把數據寫出
String str="\r\nhello world";
byte[] buf=str.getBytes();//把字符串轉爲字節數組
fileOutputStream.write(buf);//把字節數組寫出
//關閉資源
fileOutputStream.close();
}
public static void write3()throws IOException{
File file=new File("E:\\aaa.txt");
//建立數據的輸出通道
FileOutputStream fileOutputStream=new FileOutputStream(file,true);//第二個參數爲true時,寫入文件時以追加形式寫入
//
String data="abcd";
byte[] buf=data.getBytes();
fileOutputStream.write(buf,0,2);//指定開始的索引值與字節個數寫出
}
public class output_demo2 {
public static void main(String[] args) throws IOException{
write4();
}
public static void write4() throws FileNotFoundException, IOException {
File file=new File("E:\\abc.txt");
FileOutputStream fileOutputStream =new FileOutputStream(file);
fileOutputStream.write(384);
fileOutputStream.close();
}
}
練習:拷貝圖片
public class copy_picture {
public static void main(String[] args)throws IOException {
//找到目標文件
File file1=new File("E:\\picture1\\2.jpg");//源目標文件
File file2=new File("F:\\picture2\\大貓.jpg");//目的目標文件
//建立數據通道
FileInputStream fileInputStream=new FileInputStream(file1);
FileOutputStream fileOutputStream=new FileOutputStream(file2);
//讀取數據
int length=0;//記錄本次讀取的字節數
//建立緩衝字節數組
byte[] buf=new byte[1024];
//邊讀邊寫
while((length=fileInputStream.read(buf))!=-1) {
fileOutputStream.write(buf,0,length);//這樣寫保證讀到多少寫多少,不會每次都寫1024個字節,導致寫多
}
//關閉資源(原則:先開後關,後開先關)
fileOutputStream.close();
fileInputStream.close();
}
}