泛型
两个定义的时机
* 声明引用的时候
* 在继承泛型的时候
* 第二个<> 可以不写(自动补全jdk1.7之后使用)
//让类型自己可以比较, 泛型不可以用实现implements 关键字
<T extends Comparable<T>
Map(接昨天的集合)
key不能重复
value没有太多的限制
但是通常情况下, key为String
遍历方式
Set<String> keySet = map.keySet();//key转换成set但是value不能转换成set
for (String s : keySet) {
System.out.println("key => " + s);
System.out.println("value => " + map.get(s));
}
//2. 使用Entry遍历
Set<Map.Entry<String, String>> entries = map.entrySet();
for (Map.Entry<String, String> entry : entries) {
System.out.println("key => " + entry.getKey());
System.out.println("value => " + entry.getValue());
}
Collection<String> values = map.values();//仅仅是个集合, 可以使用迭代器
//只能找到values找不到相应的key(通过value是找不到key的, 废话!)
for (String value : values) {
System.out.println(value);
}
重要知识点
删除时, HashMap中, value的相等判断只需要equals, key的重复判断需要判断hashCode和equals方法
key也可以进行比较, 但是需要实现比较接口
Collections集合工具类
// Collections : 集合工具类
// Collections.sort(); : 待排序类必须可以被比较
// Collections.fill(); : 填充
List<Integer> list = new ArrayList<>();
//只能先有了再填充替换
Collections.addAll(list, 21, 4654 ,65 ,64,654);
System.out.println(list);
//二分查找: 元素一定是!升序!才能进行查找,
Collections.sort(list);
System.out.println(list);
Collections.reverse(list); //反转
System.out.println(list);
System.out.println(Collections.binarySearch(list, 21, (o1, o2) -> o2 - o1));
IO流
几种分类
流向分类
站在内存的角度出发, 例如数据读到内存中的称之为输入流.
- 输入流
- 输出流
来源分类
- 文件流
- 内存流(从内存中读取, 也输出到内存)
- 网络流
- 控制台流(System.in和System.out)
操作单元分类
字符流
字节流
设计模式分类
- 基础流
- 包装流
//FileInputStream需要一个文件地址 绝对路径和相对路径
FileInputStream fis = new FileInputStream("res/ss.mp3");
//fis.read();//读取一个字节, 返回值为int 判断结束位置, -1时读到末尾
//fis.available();//返回值的结果是无阻碍的时候获得byte的长度
注: 除了访问文本文件用字符流之外, 都是使用字节流
Java中的IO流一般都需要装饰类去装饰流对象, 就是我们一般说得装饰者设计模式
装饰者设计模式优势
- 更加灵活
- 解决java中的多继承问题
jdk1.7之后IO流异常处理
/**
* jdk1.7之后如果想让自己写的类自动调用close方法, 必须实现AutoCloseable接口
*/
//jdk1.7之后标准写法
try(FileOutputStream fos = new FileOutputStream("res/abc.txt");
BufferedOutputStream bos = new BufferedOutputStream(fos, 5)) {
//默认的append参数为: false, 如果不存在会自动创建文件
//true: 从后面追加 false:从头开始写
//fos = new FileOutputStream("res/abc.txt");
//参数int类型: 它只使用了最低的8位(<255), 大于255没有用的(当作无符号byte使用)
//fos.write(0x61);
// byte[] bytes = {97, 100, 61, 48};
// fos.write(bytes);//写入到文件中
// OutputStreamWriter osw = new OutputStreamWriter(fos, "UTF-8");
// osw.write('中');
// osw.flush();
// bos = new BufferedOutputStream(fos, 5);
bos.write('a');
bos.write('a');
//把缓冲区的所有的数据写到磁盘或者网络上
// bos.flush();
//close也会完成上述的操作, 并且将流关闭不能在进行读写了
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
Java中专门写基本数据类型和String类型的方法
try(FileOutputStream fos = new FileOutputStream("res/data.txt");
DataOutputStream dos = new DataOutputStream(fos)){
dos.writeInt(1000);
dos.writeFloat(30.56f);
//先写入short类型的字符串的长度
dos.writeUTF(" 每个 ID3V2.3 的标签都一个标签头和若干个标签帧或一个扩展标签头组成。关于曲目的信息如标题、作者\n" +
"等都存放在不同的标签帧中,扩展标签头和标签帧并不是必要的,但每个标签至少要有一个标签帧。标签\n" +
"头和标签帧一起顺序存放在 MP3 文件的首部。");
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
//写入的顺序和读取的顺序一定要一致
System.out.println(dis.readInt());
System.out.println(dis.readFloat());
System.out.println(dis.readUTF());
还有一个ObjectInputStream ObjectOutputStream: 对象的读写, 需要实现Serializable接口, Android中有其他的实现方式
public class Test05 implements Serializable{
//加上该关键字之后不需要需要序列化
private transient int i;
}
随机文件读取 RandomAccessFile
一般用来: 断电续传 多线程下载 电子书的阅读器
明天再续…