文章目录

C++文件读写(举例):

参考:
2019年2月8日训练日记(文件操作知识点小结)
文件操作的详细使用
C++文件读写详解(ofstream,ifstream,fstream)
C/C++读写文件的几种方法fstream fopen、fwrite()、fread()操作

注意事项(乱码问题):

文件读写很容易乱码,在txt读取时文档格式为ANSI则不会在屏幕输出时乱码,如果txt文件为UTF-8格式则会导致屏幕输出时乱码。
参考:c++ txt文件的读写及乱码问题解决

1、通过ifstream与getline()函数进行读取;直接通过ifstream定义的infile进行重定向输入。
例一:
#include<bits/stdc++.h>
using namespace std;
int main()
{
   
    int n = 1;
    string tem;
    ifstream infile("test.txt");
    for(int i = 0; i<n; i++)  //由getline()函数控制读到什么位置终止
    {
   
        /* getline()函数 参考: C++ getline函数用法详解: http://c.biancheng.net/view/1345.html getline() 语法: istream &getline( char *buffer, streamsize num ); istream &getline( char *buffer, streamsize num, char delim ); getline()函数用于输入流,读取字符到buffer中,直到下列情况发生: num - 1个字符已经读入, 碰到一个换行标志, 碰到一个EOF, 或者,任意地读入,直到读到字符delim。delim字符不会被放入buffer中。 */

        //getline(infile,tem);
        //getline(infile,tem,'a'); //读到文件中第一个a停止(不包含a)
        getline(infile,tem,'\t');  //默认读到\t停止,由于文件中不存在\t故读到文件末尾
        cout<<tem.c_str();  //.c_str()以C风格方式输出字符串。
    }
    //由于是getline()函数控制读到什么位置终止,所以不写到for循环内也OK
    //getline(infile,tem,'\t'); //默认读到\t停止,由于文件中不存在\t故读到文件末尾
    //cout<<tem.c_str(); //.c_str()以C风格方式输出字符串。


    //直接通过ifstream定义的infile进行重定向输入(格式不符合原文格式,需要注意格式问题)。
    /* while(infile>>tem){ cout<<tem.c_str()<<endl; } */
    return 0;
}
例二:
#include<bits/stdc++.h>
using namespace std;
int main()
{
   
    char buffer[256];
    ifstream in("test.txt");
    if (! in.is_open())
    {
   
        cout << "Error opening file";
        exit (1);
    }
    while (!in.eof() )
    {
   
        in.getline (buffer,100);  //读到每一行的换行即停止
        cout << buffer << endl;
    }
    return 0;
}
应用举例(可参考12306、图书管理系统):
void Gaotieop::load()
{
   
    Gaotie g;
    int gaotieshu_;
    ifstream infile("2018212591马俊光的车次信息.txt",ios::in);
    if(!infile)
    {
   
        cout<<"can't load Gaotie!"<<endl;
        return;
    }
    vgaotie.clear();
    gaotienumber.clear();
    gaotiename.clear();
    siteshu.clear();
    infile>>gaotieshu_;
    setGaotieshu(gaotieshu_);
    for(int i=1;i<=gaotieshu_;i++)
    {
   
        infile>>g;
        vgaotie.push_back(g);
        gaotienumber.insert(make_pair(g.getNumber(),vgaotie.size()-1));
        gaotiename.insert(make_pair(g.getName(),vgaotie.size()-1));
        siteshu.insert(make_pair(g.getSiteshu(),vgaotie.size()-1));
    }
    infile.close();
    //test
    /* cout<<getGaotieshu()<<endl; for(int i=0;i<vgaotie.size();i++) cout<<vgaotie[i]; */
}

void Gaotieop::save()
{
   
    ofstream outfile("2018212591马俊光的车次信息.txt",ios::out);
    if(!outfile)
    {
   
        cout<<"can't save Gaotie!"<<endl;
        return;
    }
    outfile<<getGaotieshu()<<endl;
    for(int i=0;i<vgaotie.size();i++)
    {
   
        if(vgaotie[i].getNumber()!="0")
        outfile<<vgaotie[i];
    }
    outfile.close();
    /* //test cout<<getGaotieshu()<<endl; for(int i=0;i<vgaotie.size();i++) cout<<vgaotie[i]; */
}
2、通过fopen()、fscanf()、fprintf()函数读取文件并复制到另一个文件中,同时打印在屏幕上。
#include<bits/stdc++.h>
#include<cstdio>
using namespace std;
int main()
{
   
    FILE *fin,*fout;
    fin=stdin;
    fout=stdout;
    fin = fopen("test.txt","rb");                    //定义输入文件名
    fout = fopen("test_out.txt","wb");              //定义输出文件名
    char temp;
    /* fscanf 语法: #include <stdio.h> int fscanf( FILE *stream, const char *format, ... ); 函数fscanf()以scanf()的执行方式从给出的文件流中读取数据. fscanf()的返回值是事实上已赋值的变量的数,如果未进行任何分配时返回EOF. */
    while (fscanf(fin,"%c",&temp)==1)   //从输入文件中读入数据
    {
   
        cout<<temp;
        fprintf(fout,"%c",temp);
    }
    fclose(fin);
    fclose(fout);                     //关闭文件,可省略
    return 0;
}
3、通过freopen()输入输出重定向来进行操作(这里只展示部分操作),可参考通讯录管理系统的文件读写。
int main()
{
   
    freopen("1.txt","r",stdin); //操作记录从文件1.txt中输入数据
    if(freopen("1.txt","r",stdin)==NULL)//(这里与fopen读取是否成功的判断方式不同)
    {
   
        cout<<"Can't read!"<<endl;
        return 0;
    }
    freopen("2.txt","w",stdout); //操作输出结果输出到自动创建的文件2.txt中

    fclose(stdin);
    fclose(stdout);

    freopen("小光的通讯录.txt","w",stdout);//操作最后的通讯录结果(所有联系人)输出到"通讯录.txt"中

    fclose(stdout);
    return 0;
}
	//fopen读取是否成功的判断
	fpSrc = fopen( "c:\\tmp\\students.txt", "rb");
    if( fpSrc == NULL )
    {
   
        printf( "Failed to open the file.");
        return 0;
    }

Java文件读写(举例):

1、通过FileInputStream与FileOutputStream文件输入输出流进行读写(以文本文件复制为例)

此段代码采用文件输入输出流,因此文档格式不限,可以是图片、视频等多种文件格式。可用于文档的复制等。
另外此段代码更可用于格式的转换,感觉超赞!测试将音乐格式.m4a转换为视频格式.mp4,视频保留了音效,界面由于本身就没有故是黑屏效果。也测试将mp4格式转换为mp3格式将音效提取出来,保留了音效。

注意内容:

	 int by = 0;
	 while ((by = fis.read()) != -1) {
    fos.write(by); }
2、通过FileReader搭配BufferedReader、FileWriter搭配BufferedWriter进行读写(以文本文件复制为例)

此段代码仅适用于文本文档读写复制。

注意内容:

	String line;
	while ((line = bw1.readLine()) != null) {
   
		bw2.write(line);
		bw2.newLine();  //换行
	}

1、2源代码:

import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.FileReader;
import java.io.FileWriter;
import java.io.File;
import java.io.BufferedReader;
import java.io.BufferedWriter;

/* * 复制文本 * * 数据源:从哪里来 * a.txt -- 读取数据 * 目的地: * b.txt * */
public class IOTest {
   
	
	//文件复制(适合所有文件)
	/* * public static void main(String[] args) throws IOException { * * FileInputStream fis = new FileInputStream("C:\\Users\\Administrator\\Desktop\\argc.txt");// 封装数据源对象 * FileOutputStream fos = new FileOutputStream("C:\\Users\\Administrator\\Desktop\\argc1.txt");// 封装目的地 * //此处可对FileInputStream与FileOutputStream使用BufferInputStream和BufferOutputStream进行包装嵌套来修饰,从而提高读写速度,详见下面的例子。 * int by = 0; * while ((by = fis.read()) != -1) { fos.write(by); } // 释放资源的时候先关闭谁都可以 * fis.close(); fos.close(); } */
	
	//格式转换
// public static void main(String[] args) throws IOException {
   
//
// FileInputStream fis = new FileInputStream("C:\\Users\\Administrator\\Desktop\\柠檬酸.mp4");// 封装数据源对象
// FileOutputStream fos = new FileOutputStream("C:\\Users\\Administrator\\Desktop\\请你吃柠檬.mp3");// 封装目的地
// // 此处可对FileInputStream与FileOutputStream使用BufferInputStream和BufferOutputStream进行包装嵌套来修饰,从而提高读写速度,详见下面的例子。
// int by = 0;
// while ((by = fis.read()) != -1) {
   
// fos.write(by);
// } // 释放资源的时候先关闭谁都可以
// fis.close();
// fos.close();
// }

	//文件转换(仅适用于文本文档)
	public static void main(String[] args) throws IOException {
   
		String pathname = "C:\\Users\\Administrator\\Desktop\\argc.txt";
		String pathname1 = "C:\\Users\\Administrator\\Desktop\\argc2.txt";
		File f = new File(pathname);
		File s = new File(pathname1);
		FileReader fw1 = new FileReader(f);
		BufferedReader bw1 = new BufferedReader(fw1);
		FileWriter fw2 = new FileWriter(s);
		BufferedWriter bw2 = new BufferedWriter(fw2);
		String line;
		// Scanner cin=new Scanner(System.in);
		while ((line = bw1.readLine()) != null) {
   
			bw2.write(line);
			bw2.newLine();  //换行
		}

		bw2.close();
		bw1.close();

	}
}
3、Java I/O是典型的装饰模式,现在对一些类进行继承和重写来重新对Java I/O进行装饰改造。

下面涉及使用BufferInputStream和BufferOutputStream对FileInputStream与FileOutputStream进行包装嵌套来修饰,从而提高读写速度。
主要改造点:自定义一个装饰器EncryptedOutputStream类对输出流进行加工。

可参考装饰模式:
装饰模式

例(InputStream):

package io_test;

import java.io.BufferedInputStream;
import java.io.DataInputStream;
import java.io.FileInputStream;
import java.io.IOException;

public class IOTest_InputStream {
   

	public static void main(String[] args) throws IOException {
   
		DataInputStream din = null;
		try {
   
			din = new DataInputStream(
					new BufferedInputStream(
							new FileInputStream("iotest.txt")
							)
					);
			byte bs[] = new byte[din.available()];
			din.read(bs);
			String content = new String(bs);
			System.out.println("文件内容==="+content);
		}finally {
   
			din.close();
		}
	}

}
例(OutputStream)(新增了自定义的装饰器EncryptedOutputStream):

package io_test;

import java.io.IOException;
import java.io.OutputStream;

public class EncrypteOutputStream extends OutputStream {
   

	private OutputStream os = null;
	public EncrypteOutputStream(OutputStream os) {
   
		this.os = os;
	}

	@Override
	public void write(int a) throws IOException {
   
		a=a+2;
		if(a>=(97+26)) {
   
			a=a-26;
		}
		this.os.write(a);
	}

}
package io_test;

import java.io.BufferedOutputStream;
import java.io.DataOutputStream;
import java.io.FileOutputStream;
import java.io.IOException;

public class IOTest {
   

	public static void main(String[] args) throws IOException {
   
		DataOutputStream dout = new DataOutputStream(
				new BufferedOutputStream(
						new EncrypteOutputStream(
								new FileOutputStream("iotest.txt"))));
		dout.write("abcd".getBytes());
		dout.close();
	}

}

iotest.txt文件下就会输出:cdef(改造之前应该为abcd)

4、文件复制(直接复制文件,使用文件流进行操作)(参考1)(这里对文本文档进行末尾添加操作,而不是覆盖已有内容)

注意内容:

		//Scanner cin = new Scanner(f); //以变量类型方式读取文件
		if(!f.exists()) {
   
			f.createNewFile();
		}
		
		FileInputStream in=new FileInputStream(f);  //直接以文件流方式读取文件
		
		byte[] b = new byte[1024];
		int c;
		
		FileOutputStream out = new FileOutputStream(fout,true);  //可追加,可更新文件后重写
		
		while((c=in.read(b))!=-1) {
   
			for(int i=0;i<c;i++) {
   
				out.write(b[i]);
			}
		}

源代码:

package txt文件读取;  //以文件流方式读取

import java.io.BufferedInputStream;  //添加buffer缓冲区,使文件读写速度更快
import java.io.BufferedOutputStream;
import java.io.File;
import java.io.FileInputStream;
//import java.io.FileNotFoundException;
import java.io.FileOutputStream;
//import java.io.FileWriter;
import java.io.IOException;
//import java.util.Scanner;

public class copy {
   //直接复制文件,使用文件流进行操作,这里选用

	public static void main(String[] args) throws IOException {
   
		String path = "C:\\Users\\Dell\\Desktop\\学生成绩1.txt";
		File f = new File(path);
		File fout = new File("C:\\Users\\Dell\\Desktop\\学生成绩2.txt");  //不同于path的命名方式
		//Scanner cin = new Scanner(f); //以变量类型方式读取文件
		if(!f.exists()) {
   
			f.createNewFile();
		}
		FileInputStream in=new FileInputStream(f);  //直接以文件流方式读取文件
		byte[] b = new byte[1024];
		int c;
		FileOutputStream out = new FileOutputStream(fout,true);  //可追加,可更新文件后重写
		
		while((c=in.read(b))!=-1) {
   
			for(int i=0;i<c;i++) {
   
				out.write(b[i]);
			}
		}
		
		BufferedInputStream bufr = new BufferedInputStream(new FileInputStream(f));  //对文件流读取方式进行改造,使文件读取速度更快
		BufferedOutputStream bufout = new BufferedOutputStream(new FileOutputStream(fout,true));
	
		while((c=bufr.read(b))!=-1) {
   
			for(int i=0;i<c;i++) {
   
				bufout.write(b[i]);
			}
		}
		
		in.close();
		out.close();
		bufr.close();
		bufout.close();
	}

}
5、从键盘读入写到文件内部(采用PrintStream写入文件)

源代码:

package txt文件读取;

import java.io.File;
import java.io.FileNotFoundException;
import java.io.PrintStream;
import java.util.Scanner;

public class keyborad {
   

	public static void main(String[] args) throws FileNotFoundException {
   
		String path = "C:\\Users\\Dell\\Desktop\\学生成绩2.txt";
		Scanner cin = new Scanner(System.in);
		File f = new File(path);
		PrintStream p = new PrintStream(f);
		String s = null;
		while(true) {
     //!s.equals("end"): Exception in thread "main" java.lang.NullPointerExceptionat txt文件读取.keyborad.main(keyborad.java:16)
			s=cin.next();
			if(s.equals("end")) {
   
				break;  //s=="end"无效,跳不出循环,证明Sting类型应当用equals比较是否一致
			}
			p.println(s);
		}
		cin.close();
		p.close();
	}

}
6、从文件读入内容进行操作后(变换大小写,统计文件字符数、行数等)输出到新文件中并打印到屏幕上(BufferedReader读入,PrintStream写入)

注意内容:

			char c;
			for(int i=0;i<str.length();i++) {
   
				c=str.charAt(i);  
				if(c==' '||c=='\n'||c=='\t');
				else count++;
				//System.out.print(Character.toLowerCase(c));
				System.out.print(Character.toUpperCase(c));  //这里只按大写为例
				p.print(Character.toUpperCase(c));
				//nNaAmMeE //大小写一起使用时效果
			}
// str.toUpperCase(); //无用,没有产生效果
// str.toLowerCase();
// System.out.println(str);

源代码:

package txt文件读取;
//以BufferReader方式读取

import java.io.BufferedReader;
import java.io.File;
//import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.IOException;
import java.io.PrintStream;

public class Systemout {
   

	public static void main(String[] args) throws IOException {
   
		String path = "C:\\Users\\Dell\\Desktop\\学生成绩2.txt";
		
		//将学生成绩2中文档经过转化后直接存到学生成绩3中
		File f = new File("C:\\Users\\Dell\\Desktop\\学生成绩3.txt");
		PrintStream p = new PrintStream(f);
		
// FileReader fr = new FileReader(f); //并不好用
		
		BufferedReader bfr = new BufferedReader(new FileReader(path));
		String str = null;
// int lineNumber = 0; //统计文本文件行数
		int count=0;  //统计字符个数
		while ((str = bfr.readLine()) != null) {
   
// lineNumber++;
// System.out.println(lineNumber + " " + str);
			
			//Character c;
			char c;
			for(int i=0;i<str.length();i++) {
   
				c=str.charAt(i);  
				if(c==' '||c=='\n'||c=='\t');
				else count++;
				//System.out.print(Character.toLowerCase(c));
				System.out.print(Character.toUpperCase(c));  //这里只按大写为例
				p.print(Character.toUpperCase(c));
				//nNaAmMeE //大小写一起使用时效果
			}
// str.toUpperCase(); //无用,没有产生效果
// str.toLowerCase();
// System.out.println(str);
			System.out.println();
			p.println();
		}
		System.out.print(count);
		bfr.close();
		p.close();
	}

}
7、以变量方式读取文件进行操作,使用Scanner读入(按格式),使用PrintStream写入(以计算学生成绩为例)

注意内容:

该程序需要用到文本文档,将在下面给出。

		String path = "C:\\Users\\Dell\\Desktop\\学生成绩1.txt";
		File f = new File(path);
		Scanner cin = new Scanner(f);
		//像正常从键盘键入一样(Scanner cin = new Scanner(System.in);):
		String s[] = new String[4];
		for(int i=0;i<4;i++) {
   
			s[i]=cin.next();
		}

源代码:

package txt文件读取;  //以变量方式读取,使用Scanner,使用PrintStream写入

//按排序顺序输出,同奖学金评定,可使用类的方式对平均分进行求出并对对象排序输出
import java.io.File;
//import java.io.FileNotFoundException;
//import java.io.FileOutputStream;
import java.io.IOException;
import java.io.PrintStream;
import java.util.Scanner;
public class txt {
   
	public static void main(String[] args) throws IOException {
   
		String path = "C:\\Users\\Dell\\Desktop\\学生成绩1.txt";
		File f = new File(path);
		Scanner cin = new Scanner(f);
		System.out.println("文件的部分属性:");
		System.out.println("文件路径:"+f.getPath());
		System.out.println("文件名:"+f.getName());
		System.out.println("文件可读性:"+f.canRead());
		System.out.println("文件可写性:"+f.canWrite());
		String s[] = new String[4];
		for(int i=0;i<4;i++) {
   
			s[i]=cin.next();
		}
		String name[] = new String [4];
		int count = 0;
		double score[][] = new double [4][4];
		for(int i=0;i<4;i++) {
   
			for(int j=0;j<4;j++) {
   
				if(j==0) {
   
					name[count]=cin.next();
					count++;
				}
				else {
   
					score[i][j-1]=cin.nextDouble();
				}
			}
			score[i][3]=(score[i][0]+score[i][1]+score[i][2])/3;
		}
		cin.close();
		
		System.out.println("初始数据:");
		
		for(int i=0;i<4;i++) {
   
			System.out.print(s[i]+" ");
		}
		System.out.println();
		
		for(int i=0;i<4;i++) {
   
			System.out.print(name[i]+" ");
			for(int j=0;j<4;j++) {
   
				System.out.print(score[i][j]+" ");
			}
			System.out.println();
		}
		
		//文件写入:(排序前数据)
		File p = new File("C:\\Users\\Dell\\Desktop\\学生成绩2.txt");
		if(!p.exists()){
   
		    p.createNewFile();
		}
				
		PrintStream out=new PrintStream(p);
		out.println("初始数据:");
				
		for(int i=0;i<4;i++) {
   
			out.print(s[i]+" ");
		}
		out.println();
		
		for(int i=0;i<4;i++) {
   
			out.print(name[i]+" ");
			for(int j=0;j<4;j++) {
   
				out.print(score[i][j]+" ");
			}
			out.println();
		}
		
		//排序:
		String a;
		double b[] = new double[4];
		for(int i=0;i<4;i++) {
   
			for(int j=0;j<4;j++) {
   
				if(score[i][3]>=score[j][3]) {
   
					a=name[i];
					name[i]=name[j];
					name[j]=a;
					for(int k=0;k<4;k++) {
   
						b[k]=score[i][k];
						score[i][k]=score[j][k];
						score[j][k]=b[k];
					}
				}
			}
		}
		
		System.out.println("排序后数据:");
		for(int i=0;i<4;i++) {
   
			System.out.print(s[i]+" ");
		}
		System.out.println();
		for(int i=0;i<4;i++) {
   
			System.out.print(name[i]+" ");
			for(int j=0;j<4;j++) {
   
				System.out.print(score[i][j]+" ");
			}
			System.out.println();
		}
		
		//文件写入:(排序后数据)
		out.println();
		out.println("排序后数据:");
		
		for(int i=0;i<4;i++) {
   
			out.print(s[i]+" ");
		}
		out.println();
		
		for(int i=0;i<4;i++) {
   
			out.print(name[i]+" ");
			for(int j=0;j<4;j++) {
   
				out.print(score[i][j]+" ");
			}
			out.println();
		}
		
		out.close();
	}
}

该程序需要的文档:

学生成绩1.txt

姓名 数学 物理 化学
张三 98 80 89 
李四 91 88 87
王五 93 89 78
周六 90 90 89

结果展示文档(结果展示,自动生成):

学生成绩2.txt

初始数据:
姓名 数学 物理 化学 
张三 98.0 80.0 89.0 89.0 
李四 91.0 88.0 87.0 88.66666666666667 
王五 93.0 89.0 78.0 86.66666666666667 
周六 90.0 90.0 89.0 89.66666666666667 

排序后数据:
姓名 数学 物理 化学 
周六 90.0 90.0 89.0 89.66666666666667 
张三 98.0 80.0 89.0 89.0 
李四 91.0 88.0 87.0 88.66666666666667 
王五 93.0 89.0 78.0 86.66666666666667