输入输出流。
InputStream与OutputStream 读与写
void readAndWriteWithIOStream(String inputFileName, String outputFileName)
throws IOException {
File outputFile = new File(outputFileName);
if (!outputFile.exists()) {
outputFile.createNewFile();
}
InputStream inputStream = new FileInputStream(inputFileName);
BufferedInputStream bufferedInputStream = new BufferedInputStream(inputStream);
BufferedOutputStream bufferedOutputStream =
new BufferedOutputStream(new FileOutputStream(outputFile));
int byteSize = 1024;
int count = 0;
byte[] bytes = new byte[byteSize];
try {
while ((count = bufferedInputStream.read(bytes)) > 0) {
bufferedOutputStream.write(bytes, 0, count);
}
} finally {
IOUtil.close(bufferedInputStream);
IOUtil.close(bufferedOutputStream);
}
}
使用InputStream读取字节并转为字符串
String readWithInputStream(String inputFileName)
throws IOException {
InputStream inputStream = new FileInputStream(inputFileName);
BufferedInputStream bufferedInputStream = new BufferedInputStream(inputStream);
int byteSize = 1024;
int count = 0;
byte[] bytes = new byte[byteSize];
String line = null;
StringBuilder stringBuilder = new StringBuilder();
try {
while ((count = bufferedInputStream.read(bytes)) > 0) {
line = new String(bytes, 0, count, Charset.forName("UTF-8"));
stringBuilder.append(line);
}
} finally {
IOUtil.close(bufferedInputStream);
}
return stringBuilder.toString();
}
输入流的复用
判断是否支持复用:boolean InputStream#markSupported()
标记:InputStream#inputStream.mark(int)
重置:InputStream#inputStream.reset()
void read(InputStream inputStream) throws IOException {
if (!inputStream.markSupported()) {
//包装
inputStream = new BufferedInputStream(inputStream);
}
byte[] bytes = new byte[32];
//标记
inputStream.mark(0);
//第一次读
inputStream.read(bytes);
String s = new String(bytes, Charset.forName("utf8"));
System.out.println(s);
//重置
inputStream.reset();
//第二次读
inputStream.read(bytes);
inputStream.close();
s = new String(bytes, Charset.forName("utf8"));
System.out.println(s);
}
//构造输入流
InputStream getInputStream(String filePath) throws FileNotFoundException {
return new FileInputStream(new File(filePath));
}
第一次读和第二次读,内容相同,内部维护一个数组,东西读出来存在数组里面,之后就是操作数组了。
InputStream#mark(int readlimit)
函数,标记当前位置,并保证在mark以后最多可以读取readlimit字节数据,mark标记仍有效。如果在mark后读取超过readlimit字节数据,mark标记就会失效。但是,判断mark标记位是否仍有效的并不是只有readlimit一个参数,还有内部缓冲区的大小,public BufferedInputStream(InputStream in, int size)
,默认缓冲区大小int DEFAULT_BUFFER_SIZE = 8192
,8192字节,如果待读取文件大于8192字节,还大于readlimit字节,再调用BufferedInputStream#reset()
就会报java.io.IOException: Resetting to invalid mark
。
看BufferedInputStream#read()中调用的fill()函数。
private void fill() throws IOException {
byte[] buffer = getBufIfOpen();
if (markpos < 0)
pos = 0; /* no mark: throw away the buffer */
else if (pos >= buffer.length) /* no room left in buffer */
if (markpos > 0) { /* can throw away early part of the buffer */
int sz = pos - markpos;
System.arraycopy(buffer, markpos, buffer, 0, sz);
pos = sz;
markpos = 0;
} else if (buffer.length >= marklimit) {
markpos = -1; /* buffer got too big, invalidate mark */
pos = 0; /* drop buffer contents */
}
...
readlimit是int型的,也就是说最多也只能保存 Integer.MAX_VALUE
个字节。缓冲区使用byte[]数组保存字节的,byte[]数组最大长度是 Integer.MAX_VALUE
个字节。
ObjectInputStream与ObjectOutputStream
用于对象的序列化:
public static void main(String[] args) throws IOException, ClassNotFoundException {
String fileName = "E:\\temp\\obj.txt";
SerA serA = new SerA();
serA.setName("pepelu");
ObjectOutputStream objectOutputStream =
new ObjectOutputStream(new FileOutputStream(fileName));
objectOutputStream.writeObject(serA);
ObjectInputStream objectInputStream = new ObjectInputStream(
new FileInputStream(fileName));
SerA sa = (SerA) objectInputStream.readObject();
objectInputStream.close();
objectOutputStream.close();
System.out.println(sa.getName());
System.out.println(serA == sa);
}
/* SerA.java */
public class SerA implements Serializable {
private static final long serialVersionUID = 1L;
private String name;
public void setName(String name) {
this.name = name;
}
public String getName() {
return name;
}
}
output:
pepelu
false
这两个对象并不是同一个对象,至少在堆上的地址不同。
BufferedReader读取字符串
String readWithReader(InputStream inputStream) throws IOException {
BufferedReader bufferedReader = new BufferedReader(
new InputStreamReader(inputStream, Charset.forName("UTF-8")));
String line = null;
StringBuilder stringBuilder = new StringBuilder();
try {
while ((line = bufferedReader.readLine()) != null) {
stringBuilder.append(line).append("\n");
}
} finally {
IOUtil.close(bufferedReader);
}
return stringBuilder.toString();
}
BufferedWriter写字符串
void writeWithBufferedWriter(String outputFileName) throws IOException {
BufferedWriter bufferedWriter = new BufferedWriter(
new OutputStreamWriter(new FileOutputStream(outputFileName)));
try {
bufferedWriter.write("hello,bitch");
} finally {
bufferedWriter.close();
}
}
IOUtil关闭流
public static void close(Closeable closeable) {
if (closeable == null) {
return;
}
try {
closeable.close();
} catch (IOException e) {
e.printStackTrace();
}
}