04、※NIO的理解、NIO的概念、缓冲区的读取数据、mark标志位置、reset回设的操作和通道文本数据获取与文本写出、生成电影票和文件中的内容和编写一个程序,是将两个文件的内容合并到一个文件中

※NIO的理解

    • NIO的概念
    • ※--Buffer 缓冲区
      • 读取数据
      • mark标志位置的概念和reset回设的操作
    • ※--Channel【读写方法】 通道.
      • NIO通道和缓冲区实现文件数据获取
      • NIO-使用通道和缓冲区实现文本写出
      • NIO实现文本赋值操作
      • NIO-使用通道的map方法实现映射数据操作
    • 练习1:生成电影票和文件中的内容
      • 实现方法一:
      • 实现方法二:
    • 练习二: 编写一个程序,其功能是将两个文件的内容合并到一个文件中。
      • 实现一
      • 实现二

NIO的概念

–传统的IO流【本质上都是基于字节流】会进行【阻塞】操作、【一个字节一个字节操作
NIO【提供非阻塞的操作】【将数据以区域的形式映射到内存】【性能较高】【复杂、较难理解】

–NIO提供了一个区域块的数据映射、异步的IO流操作【selector】
通道是用于获取流中数据
缓冲区是用于保存通道中的数据
–NIO是将数据映射到内存,所以NIO的传输效率传统的IO流要好

※–Buffer 缓冲区

04、※NIO的理解、NIO的概念、缓冲区的读取数据、mark标志位置、reset回设的操作和通道文本数据获取与文本写出、生成电影票和文件中的内容和编写一个程序,是将两个文件的内容合并到一个文件中_第1张图片

/* 缓冲区中的四个核心属性:

  • capacity:容量,表示缓冲区中最大存储数据的容量。一旦声明不能改变。
  • limit:界限,表示缓冲区中可以操作数据的大小。(limit后数据不能进行读写)
  • position:位置,表示缓冲区中正在操作数据的位置。
  • mark:标记,表示记录当前position位置。可以通过reset()恢复到mark的位置。
    /
    –API:
    allocate();
    put();
    flip();
    get();
    clear();
    /
    • 根据数据类型的不同(boolean 除外),有以下 Buffer 常用子类:
    • ByteBuffer
    • CharBuffer
    • ShortBuffer
    • IntBuffer
    • LongBuffer
    • FloatBuffer
    • DoubleBuffer
    • 上述缓冲区的管理方式几乎一致,通过allocate()获取缓冲区
      */
      04、※NIO的理解、NIO的概念、缓冲区的读取数据、mark标志位置、reset回设的操作和通道文本数据获取与文本写出、生成电影票和文件中的内容和编写一个程序,是将两个文件的内容合并到一个文件中_第2张图片
/**
 * @author Lantzrung
 * @date 2022年8月3日
 * @Description
 */
package com.daily01;

import java.nio.ByteBuffer;


public class BufferDemo {

    // 缓冲区用于存放数据
    // NIO中缓冲区的的使用
    public static void main(String[] args) {

	// 字节缓冲区 allocate实例化方法(容量) 本质也是数组(ByteBuffer 源码中有:final byte[] hb; )
	// ByteBuffer buffer = new ByteBuffer();// 因为ByteBuffer是抽象类不能实例化对象public
	// abstract class ByteBuffer

	// 因此ByteBuffer里面提供了一个方法进行使用 capacity是容量的意思
	ByteBuffer buffer = ByteBuffer.allocate(100);// 设定容量长度为100
	// 缓冲区的属性
	System.out.println("position=" + buffer.position());// position=0
	System.out.println("limit=" + buffer.limit()); // limit=100
	System.out.println("capacity=" + buffer.capacity());// capacity=100

	// 存放数据
	buffer.put((byte) 97);
	buffer.put((byte) 98);
	buffer.put((byte) 99);

	// 缓冲区的属性
	System.out.println("--------------存放数据后-------------");
	System.out.println("position=" + buffer.position());// position=3
	System.out.println("limit=" + buffer.limit()); // limit=100
	System.out.println("capacity=" + buffer.capacity());// capacity=100

//	OPEN1
//	// 从缓冲区中读取数据
//	// 为啥读取的数据get为0? 因为position从3开始进行获取 所以要进行把position设置为0 limit设置为3
//	System.out.println(buffer.get());// 0
//	System.out.println(buffer.get());// 0
//	System.out.println(buffer.get());// 0
//	System.out.println("position=" + buffer.position());// position=3
//	System.out.println("limit=" + buffer.limit()); // limit=100
//	System.out.println("capacity=" + buffer.capacity());// capacity=100

	System.out.println("----------------设置后---------------");
//	OPEN2
	// 从缓冲区中读取数据
	// 为啥读取的数据get为0? 因为position从3开始进行获取 所以要进行把position设置为0 limit设置为3
	buffer.position(0);// 把position设置为0
	buffer.limit(3);// 把buffer设置为3
	System.out.println(buffer.get());// 97
	System.out.println(buffer.get());// 98
	System.out.println(buffer.get());// 99
	System.out.println("position=" + buffer.position());// position=3
	System.out.println("limit=" + buffer.limit()); // limit=100
	System.out.println("capacity=" + buffer.capacity());// capacity=100

	
	System.out.println("----------------翻转设置后--------------------");
//	OPEN3
	// 要是不知道缓冲区存放了多少个数组该怎么办?
	// 翻转的作用:limit设置为position; position设置为0
	buffer.flip();
	System.out.println(buffer.get());// 97
	System.out.println(buffer.get());// 98
	System.out.println(buffer.get());// 99
	System.out.println("position=" + buffer.position());// position=3
	System.out.println("limit=" + buffer.limit()); // limit=100
	System.out.println("capacity=" + buffer.capacity());// capacity=100

	
	// 重新使用,进行清空
	buffer.clear();
	System.out.println("--------------------清空数据后---------------");
	System.out.println("position=" + buffer.position());// position=0
	System.out.println("limit=" + buffer.limit()); // limit=100
	System.out.println("capacity=" + buffer.capacity());// capacity=100
	
    }

}

读取数据

/**
 * @author Lantzrung
 * @date 2022年8月3日
 * @Description
 */
package com.daily01;

import java.nio.ByteBuffer;

public class BufferDemo03 {
    public static void main(String[] args) {

	//
	ByteBuffer buffer = ByteBuffer.allocate(100);
	buffer.put("dadafaewffioaiohfdaeewq".getBytes());
	System.out.println("-------------------存放后翻转----------------");
	//
	buffer.flip();
	System.out.println("position=" + buffer.position());
	System.out.println("limit=" + buffer.limit());
	System.out.println("capacity=" + buffer.capacity());
	// 读取
	byte[] bu = new byte[20];
	buffer.get(bu);
	System.out.println(new String(bu));// dadafaewffioaiohfdae
	// 超过limit会出现异常Exception in thread "main" java.nio.BufferUnderflowException
	buffer.get(bu);
	System.out.println(new String(bu));// dadafaewffioaiohfdae
    }

}

mark标志位置的概念和reset回设的操作

/**
 * @author Lantzrung
 * @date 2022年8月3日
 * @Description
 */
package com.daily01;

import java.nio.ByteBuffer;

public class BufferDemo03 {
    public static void main(String[] args) {

	//
	ByteBuffer buffer = ByteBuffer.allocate(100);
	buffer.put("dadafaewffioaiohfdaeewq".getBytes());
	System.out.println("-------------------存放后翻转----------------");
	//
	buffer.flip();
	System.out.println("position=" + buffer.position());// position=0
	System.out.println("limit=" + buffer.limit());// limit=23
	System.out.println("capacity=" + buffer.capacity());// capacity=100
	// 标记位置 当前position的位置 ,可以通过resert方法进行把position设置为mark位置
	buffer.mark();
	System.out.println("-------------------标记位置后--------------------");
	// 读取
	byte[] bu = new byte[20];
	buffer.get(bu);
	System.out.println(new String(bu));// dadafaewffioaiohfdae

	System.out.println("---------------回设后-------------------");
	// 回设操作reset();
	buffer.reset();
	System.out.println("position=" + buffer.position());// position=0
	System.out.println("limit=" + buffer.limit());// limit=23
	System.out.println("capacity=" + buffer.capacity());// capacity=100
	buffer.get(bu);
	System.out.println(new String(bu));// dadafaewffioaiohfdae
    }

}

※–Channel【读写方法】 通道.

Channel接口的主要实现类:
FileChannel 本地文件传输通道【阻塞】
SocketChannel/ServerSocketChannel TCP协议数据传输通道【非阻塞】
DatagramChannel UDP协议传输通道
本地IO:FileInputStream、FileOutputStream、RandomAccessFile

–通道,通过流的getChannel方法来获取通道的对象
–API:
//将通道中的数据映射到buff中,其中第一个参数为操作模式,第二个参数为操作的开始位置,第三个参数为映射的个数
map(FileChannel.MapMode.READ_ONLY, 0, file.length());

案例:
读出某个文件的数据
将buff中的数据通过通道写出文件中
实现文件的拷贝

NIO通道和缓冲区实现文件数据获取

/**
 * @author Lantzrung
 * @date 2022年8月4日
 * @Description
 */
package com.daily01;

import java.io.FileInputStream;
import java.io.IOException;
import java.nio.ByteBuffer;
import java.nio.channels.FileChannel;

public class ChannelDemo {
    public static void main(String[] args) throws IOException {
	// 通过通道来传输数据,使用缓冲区来进行乘载
	// 通道 --获取通道 --通过流来获取
	FileInputStream out = new FileInputStream("D:\\test\\data.txt");
	FileChannel channel = out.getChannel();
	// 缓冲区 -- 字节缓冲区
	ByteBuffer buffer = ByteBuffer.allocate(1024);
	//
	int len = 0;
	byte[] bu = new byte[1024];
	while ((len = channel.read(buffer))!=-1) {
	    // 预约
	    buffer.flip();
	    // 从缓冲区中获取数据
	    buffer.get(bu,0,len);
	    // 转换为字符串输出
	    System.out.println(new String(bu,0,len));
	}
	// 关闭通道、流
	channel.close();
	out.close();
    }
}

NIO-使用通道和缓冲区实现文本写出

/**
 * @author Lantzrung
 * @date 2022年8月4日
 * @Description
 */
package com.daily01;

import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.nio.ByteBuffer;
import java.nio.channels.FileChannel;
import java.util.Scanner;

public class ChannelDemo01 {
    public static void main(String[] args) throws IOException {
	write();
    }

    public static void write() throws IOException {
	// 通过通道来传输数据,使用缓冲区来进行乘载
	// 通道 --获取通道 --通过流来获取
	FileOutputStream out = new FileOutputStream("D:\\test\\data.txt");
	FileChannel channel = out.getChannel();
	// 缓冲区 -- 字节缓冲区
	ByteBuffer buffer = ByteBuffer.allocate(1024);
	//
	Scanner sc = new Scanner(System.in);
	// 进行读取操作 ---从通道中读取到了缓冲区
	while (true) {
	    // 输入信息
	    System.out.println("请输入信息:");
	    String line = sc.next();
	    // 退出循环
	    if (line.equals("exit")) {
		break;
	    }
	    // 从缓冲区中获取数据
	    buffer.put(line.getBytes());
	    // 翻转
	    buffer.flip();
	    // 通过通道写出数据
	    channel.write(buffer);
	    // 清空缓冲区
	    buffer.clear();
	}
	// 关闭通道、流
	sc.close();
	channel.close();
	out.close();
    }

    public static void read() throws IOException {
	// 通过通道来传输数据,使用缓冲区来进行乘载
	// 通道 --获取通道 --通过流来获取
	FileInputStream input = new FileInputStream("D:\\test\\data.txt");
	FileChannel channel = input.getChannel();
	// 缓冲区 -- 字节缓冲区
	ByteBuffer buffer = ByteBuffer.allocate(1024);
	// 运输
	int len = 0;
	byte[] bu = new byte[1024];
	// 进行读取操作 ---从通道中读取到了缓冲区
	while ((len = channel.read(buffer)) != -1) {
	    // 缓冲区翻转
	    buffer.flip();
	    // 从缓冲区中获取数据
	    buffer.get(bu, 0, len);
	    // 转换为字符串输出
	    System.out.println(new String(bu, 0, len));
	}
	// 关闭通道、流
	channel.close();
	input.close();
    }

}

NIO实现文本赋值操作

/**
 * @author Lantzrung
 * @date 2022年8月4日
 * @Description
 */
package com.daily01;

import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.nio.ByteBuffer;
import java.nio.channels.FileChannel;

public class ChannelCopyDemo {

    public static void main(String[] args) throws IOException {
	// 1、构建流和通道 输入流
	FileInputStream input = new FileInputStream("D:\\test\\test.txt");
	FileChannel inChannel = input.getChannel();
	// 2、构建流和通道 输出流
	FileOutputStream out = new FileOutputStream("D:\\test\\test.txt");
	FileChannel outChannel = out.getChannel();

	// 2、缓冲区--字节缓冲区
	ByteBuffer buffer = ByteBuffer.allocate(1024);// 在当前设置缓冲区为1024
	// 单词读取的长度
	int len = 0;
	// 3、循环运输数据
	while ((len = inChannel.read(buffer)) != -1) { // 从输入的通道中读取数据到缓冲区
	    // 翻转
	    buffer.flip();
	    // 写出操作到输出通道
	    outChannel.write(buffer);
	    // 准备下一次的操作清空
	    buffer.clear();
	}
	// 4、关闭资源
	inChannel.close();
	input.close();
	outChannel.close();
	out.close();
    }
}

NIO-使用通道的map方法实现映射数据操作

// 2、缓冲区 -- 字节缓冲区 映射到内存中进行复制
ByteBuffer buffer = inChannel.map(FileChannel.MapMode.READ_ONLY, 0, file.length());
/**
 * @author Lantzrung
 * @date 2022年8月4日
 * @Description
 */
package com.daily01;

import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.nio.ByteBuffer;
import java.nio.channels.FileChannel;

public class ChannelDemo02 {
    public static void main(String[] args) throws IOException {

	read();
    }

    public static void read() throws IOException {
	// 通过通道来传输数据,使用缓冲区来进行乘载
	// 通道--获取通道--通过流来获取
	File file = new File("D:\\test\\test.txt");

	FileInputStream input = new FileInputStream(file);
	FileChannel channel = input.getChannel();
	// 缓冲区 - 字节流缓冲区 把通道中的数据映射到缓冲区中存储
	// 注意:映射数据时候。注意长度不能超过文件的长度 【关键逻辑:偏移量的算法、映射长度的算法】
	ByteBuffer buffer = channel.map(FileChannel.MapMode.READ_ONLY, 0, file.length());
	// 运输
	byte[] bu = new byte[1024];
	// 偏移量
	buffer.get(bu, 0, (int) (file.length()));
	// 输出数组
	System.out.println(new String(bu));
	// 关闭通道、流
	channel.close();
	input.close();
    }
}

练习1:生成电影票和文件中的内容

04、※NIO的理解、NIO的概念、缓冲区的读取数据、mark标志位置、reset回设的操作和通道文本数据获取与文本写出、生成电影票和文件中的内容和编写一个程序,是将两个文件的内容合并到一个文件中_第3张图片

生成了电影票:
在这里插入图片描述
文件中的内容:
04、※NIO的理解、NIO的概念、缓冲区的读取数据、mark标志位置、reset回设的操作和通道文本数据获取与文本写出、生成电影票和文件中的内容和编写一个程序,是将两个文件的内容合并到一个文件中_第4张图片

实现方法一:

package com.work01;

/**
 * @author Lantzrung
 * @date 2022年8月3日
 * @Description
 */
import java.io.BufferedWriter;
import java.io.File;
import java.io.FileWriter;
import java.io.IOException;
import java.util.ArrayList;
import java.util.InputMismatchException;
import java.util.Scanner;

public class HomeWork1 {
    // 存放电影的集合
    public static ArrayList<Film> arrayList = new ArrayList<>();
    // 定义一个路径内容
    public static final String PATH = "D:\\test\\";

    public static void main(String[] args) throws IOException {
	// 开始
	tck tck = start();
	try {
	    // 生成电影票文件
	    generatetck(tck);
	} catch (RuntimeException e) {
	    System.out.println(e.getMessage());
	    // 没有生成,再次开始
	    start();
	}
    }

    // 开始
    private static tck start() {
	// 系统开始:打印电影列表+座位
	systemStarts();
	// 电影票
	tck tck = null;
	// 电影票为null,一直循环
	while (tck == null) {
	    // 输入电影票信息
	    tck = enterInformation();
	}
	return tck;
    }

    // 生成电影票文件
    private static void generatetck(tck tck) throws IOException {
	// 计算电影票价格
	String price = null;
	// 电影票价格
	for (Film f : arrayList) {
	    if (f.getName().equals(tck.getName()) && f.getTime().equals(tck.getTime())) {
		// 折扣
		final double dis = tck.getDiscount() / 10.0;
		final double v = f.getPrice() * dis;
		price = String.valueOf(v);
	    }
	}
	// 拼接文件路径+文件名
	final String[] split = tck.getTime().split(":");
	String fileName = tck.getName() + "-" + tck.getPosition() + "座-" + split[0] + "时" + split[1] + "分" + ".txt";
	final File file = new File(PATH + fileName);
	// --------------
	FileWriter writer = new FileWriter(file);
	final BufferedWriter bw = new BufferedWriter(writer);
	// --------------
	bw.write("***************************");
	bw.newLine();
	bw.write("      淘宝影院(" + tck.getType() + ")");
	bw.newLine();
	bw.write("---------------------------");
	bw.newLine();
	bw.write("  电影名:" + tck.getName());
	bw.newLine();
	bw.write("  时间:" + tck.getTime());
	bw.newLine();
	bw.write("  座位号:" + tck.getPosition());
	bw.newLine();
	bw.write("  价格:" + price);
	bw.newLine();
	bw.write("***************************");
	bw.newLine();
	System.out.println("电影票已生成!");
	// 同步刷新
	bw.flush();
	// --------------
	// 关闭流,释放资源
	bw.close();
	writer.close();
    }

    // 输入电影票信息
    private static tck enterInformation() {
	// 输入
	Scanner sc = new Scanner(System.in);
	// 电影票
	final tck tck = new tck();

	System.out.print("请输入电影名称:");
	tck.setName(sc.nextLine());

	System.out.println("请输入电影播放时间:以xx:xx的格式");
	tck.setTime(sc.nextLine());

	System.out.println("请输入你所要购买的票的类型:1.普通票  2.学生票  3.赠送票");
	int type;
	try {
	    type = sc.nextInt();
	} catch (InputMismatchException e) {
	    System.out.println("输入错误");
	    return null;
	}
	if (type == 1) {
	    tck.setType("普通票");
	} else if (type == 2) {
	    tck.setType("学生票");
	} else if (type == 3) {
	    tck.setType("赠送票");
	} else {
	    return null;
	}

	System.out.println("请输入您所需要的折扣:1-9的整数");
	try {
	    tck.setDiscount(sc.nextInt());
	} catch (InputMismatchException e) {
	    System.out.println("输入错误");
	    return null;
	}
	if (tck.getDiscount() < 0 || tck.getDiscount() > 9) {
	    System.out.println("输入错误");
	    return null;
	}

	System.out.println("请输入您所需要的座位号:以排-列的形式");
	tck.setPosition(sc.next());
	// -----------
	return tck;
    }

    // 系统开始:打印电影列表+座位
    private static void systemStarts() {
	arrayList.clear();
	final Film film1 = new Film("1.", "非常完美", "perfect", "阴萌", "范冰冰", "Romance", 60, "09:00");
	final Film film2 = new Film("2.", "非常完美", "perfect", "阴萌", "范冰冰", "Romance", 60, "13:00");
	final Film film3 = new Film("3.", "少林足球", "shaolin", "周星驰", "周星驰", "Romance", 70, "14:00");
	arrayList.add(film1);
	arrayList.add(film2);
	arrayList.add(film3);
	System.out.printf("%-2s\t%-5s\t%-5s\t%-5s\t%-5s\t%-5s\t%-5s\t%-5s\n", "序号", "电影名称", "英文名称", "导演", "演员", "电影类型",
		"价格", "时间");
	for (Film film : arrayList) {
	    System.out.printf("%-2s\t%-5s\t%-5s\t%-5s\t%-5s\t%-5s\t%-5s\t%-5s\n", film.getId(), film.getName(),
		    film.getEnglish_Name(), film.getDirector(), film.getActor(), film.getType(), film.getPrice(),
		    film.getTime());
	}
	System.out.println("下面为影院的座位结构图:");
	System.out.println("                     屏幕");
	for (int i = 1; i <= 5; i++) {
	    for (int j = 1; j <= 7; j++) {
		System.out.print("   " + i);
		System.out.print("-" + j);
	    }
	    System.out.println();
	}
    }
}

class Film {

    private String id;
    private String name;
    private String English_Name;// 英文名字
    private String director;// 导演
    private String actor; // 演员
    private String type;// 类型
    private int price;// 价格
    private String time;// 时间

    public Film() {
    }

    public Film(String id, String name, String English_Name, String director, String actor, String type, int price,
	    String time) {
	this.id = id;
	this.name = name;
	this.English_Name = English_Name;
	this.director = director;
	this.actor = actor;
	this.type = type;
	this.price = price;
	this.time = time;
    }

    @Override
    public String toString() {
	return "Film{" + "id='" + id + '\'' + ", name='" + name + '\'' + ", English_Name='" + English_Name + '\''
		+ ", director='" + director + '\'' + ", actor='" + actor + '\'' + ", type='" + type + '\'' + ", price="
		+ price + ", time='" + time + '\'' + '}';
    }

    public String getId() {
	return id;
    }

    public void setId(String id) {
	this.id = id;
    }

    public String getName() {
	return name;
    }

    public void setName(String name) {
	this.name = name;
    }

    public String getEnglish_Name() {
	return English_Name;
    }

    public void setEnglish_Name(String English_Name) {
	this.English_Name = English_Name;
    }

    public String getDirector() {
	return director;
    }

    public void setDirector(String director) {
	this.director = director;
    }

    public String getActor() {
	return actor;
    }

    public void setActor(String actor) {
	this.actor = actor;
    }

    public String getType() {
	return type;
    }

    public void setType(String type) {
	this.type = type;
    }

    public int getPrice() {
	return price;
    }

    public void setPrice(int price) {
	this.price = price;
    }

    public String getTime() {
	return time;
    }

    public void setTime(String time) {
	this.time = time;
    }
}

class tck {
    // 名称
    private String name;
    // 时间
    private String time;
    // 类型:普通票,学生票,赠送票
    private String type;
    // 折扣:1-9
    private Integer discount;
    // 位置
    private String position;

    public tck() {
    }

    public tck(String name, String time, String type, Integer discount, String position) {
	this.name = name;
	this.time = time;
	this.type = type;
	this.discount = discount;
	this.position = position;
    }

    @Override
    public String toString() {
	return "tck{" + "name='" + name + '\'' + ", time='" + time + '\'' + ", type='" + type + '\'' + ", discount="
		+ discount + ", position='" + position + '\'' + '}';
    }

    public String getName() {
	return name;
    }

    public void setName(String name) {
	this.name = name;
    }

    public String getTime() {
	return time;
    }

    public void setTime(String time) {
	this.time = time;
    }

    public String getType() {
	return type;
    }

    public void setType(String type) {
	this.type = type;
    }

    public Integer getDiscount() {
	return discount;
    }

    public void setDiscount(Integer discount) {
	this.discount = discount;
    }

    public String getPosition() {
	return position;
    }

    public void setPosition(String position) {
	this.position = position;
    }
}

实现方法二:

package com.day0803.homework;

import java.io.BufferedReader;
import java.io.FileOutputStream;
import java.io.FileReader;
import java.io.IOException;
import java.io.PrintStream;
import java.util.Scanner;

public class HomeWork1 {

	public static void main(String[] args) throws IOException {
		// 1、电影信息的获取【文件】【缓冲字符流】
		BufferedReader reader = new BufferedReader(new FileReader("D:\\GZ2244\\0803\\ticket.txt"));
		// Scanner
		Scanner sc = new Scanner(System.in);
		// 2、循环读取
		String line = "";
		while ((line = reader.readLine()) != null) {
			// 打印输出
			System.out.println(line);
		}
		// 3、座位号
		System.out.println("下面是影院的座位结构:");
		System.out.println("\t\t\t屏幕");
		// 循环
		for (int i = 1; i <= 5; i++) {
			for (int j = 1; j <= 7; j++) {
				System.out.print(i + "-" + j + "\t");
			}
			// 换行
			System.out.println();
		}
		// 获取电影购买的信息:
		System.out.println("请输入电影名称:");
		String movie = sc.next();
		System.out.println("请输入电影的播放时间,以xx点xx分的格式 :");
		String time = sc.next();
		System.out.println("请输入电影价格 :");
		double price = Double.parseDouble(sc.next());
		System.out.println("请输入购票类型,1.普通票【打折】 2.学生票【6折】 3.赠送票【免费】:");
		String type = sc.next();
		type = type.equals("1") ? "普通票" : (type.equals("2") ? "学生票" : "赠送票");
		int discount = 10;// 默认没有打折
		if (type.equals("普通票")) {
			System.out.println("请输入折扣:");
			discount = Integer.parseInt(sc.next());
			// 价格
			price = price * (discount * 0.1);
		}
		if (type.equals("学生票")) {
			// 价格
			price = price * 0.6;
		}
		if (type.equals("赠送票")) {
			// 价格
			price = 0;
		}
		System.out.println("请输入选择座位号,以排-列的形式:");
		String set = sc.next();
		// 生成电影票【文件】【打印流】
		// 文件路径
		String path = "D:\\GZ2244\\0803\\" + movie + "-" + time + "-" + set + ".txt";
		System.out.println(path);
		// 打印流
		PrintStream ps = new PrintStream(new FileOutputStream(path));
		ps.println("*******************************************");
		ps.println("***********淘宝影院(" + type + ")*************");
		ps.println("*******************************************");
		ps.println("电影名:" + movie);
		ps.println("时间:" + time);
		ps.println("座位号:" + set);
		// 先把数据读取时存在在集合中,然后遍历判断名称和时间,再通过字符串的截取获取价格,最后价格乘以折扣
		ps.println("价格:" + price + "元");
		ps.println("*******************************************");
		ps.flush();
		// 关闭流
		reader.close();
		ps.close();
		sc.close();
	}

}

练习二: 编写一个程序,其功能是将两个文件的内容合并到一个文件中。

data1.txt和data2.txt   --->  result.txt
--要求:nio

实现一

/**
 * @author Lantzrung
 * @date 2022年8月3日
 * @Description
 */
package com.work01;

import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.nio.ByteBuffer;
import java.nio.channels.FileChannel;

public class HomeWork2 {
    public static void main(String[] args) throws IOException {
	// 1、构建流和通道
	FileInputStream input = new FileInputStream("D:\\test\\data1.txt");
	FileChannel inChannel = input.getChannel();
	FileInputStream input1 = new FileInputStream("D:\\test\\data2.txt");
	FileChannel inChanne2 = input1.getChannel();
	//
	FileOutputStream out = new FileOutputStream("D:\\test\\result.txt", true);
	FileChannel outChannel = out.getChannel();

	// 2、缓冲区 -- 字节缓冲区
	ByteBuffer buffer = ByteBuffer.allocate(1024);
	int len = 0;// 单次读取的长度
	// 3、循环运输数据
	while ((len = inChannel.read(buffer)) != -1) {// 从输入的通道中读取数据到缓冲区
	    // 翻转
	    buffer.flip();
	    // 写出数据到输出的通道
	    outChannel.write(buffer);
	    // 准备下一次的操作,清空
	    buffer.clear();
	}
	int len1 = 0;// 单次读取的长度
	// 3、循环运输数据
	while ((len1 = inChanne2.read(buffer)) != -1) {// 从输入的通道中读取数据到缓冲区
	    // 翻转
	    buffer.flip();
	    // 写出数据到输出的通道
	    outChannel.write(buffer);
	    // 准备下一次的操作,清空
	    buffer.clear();
	}
	// 4、关闭流、通道
	inChannel.close();
	input.close();
	inChanne2.close();
	input1.close();
	outChannel.close();
	out.close();
    }
}

实现二

package com.day0803.homework;

import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.nio.ByteBuffer;
import java.nio.channels.FileChannel;

public class HomeWork2 {

	public static void main(String[] args) throws IOException {
		// 1、创建Nio【通道、缓冲区】【内存映射】
		// 文件1 通道
		File file1 = new File("D:\\test\\data1.txt");
		FileInputStream input1 = new FileInputStream(file1);
		FileChannel channel1 = input1.getChannel();
		// 文件2 通道
		File file2 = new File("D:\\test\\data2.txt");
		FileInputStream input2 = new FileInputStream(file2);
		FileChannel channel2 = input2.getChannel();
		// 文件输出文件 的 通道
		FileOutputStream out = new FileOutputStream("D:\\test\\result.txt");
		FileChannel out_channel = out.getChannel();
		// 文件1读取写出
		ByteBuffer buffer = channel1.map(FileChannel.MapMode.READ_ONLY, 0, file1.length());
		out_channel.write(buffer);
		// 偏移position
		out_channel.position(file1.length());
		// 文件2 读取写出
		buffer = channel2.map(FileChannel.MapMode.READ_ONLY, 0, file2.length());
		out_channel.write(buffer);
		// 关闭流
		input1.close();
		channel1.close();
		input2.close();
		channel2.close();
		out.close();
		out_channel.close();
	}
}

你可能感兴趣的:(05,IO流和多线程,nio,java,jvm,开发语言,算法)