数据结构
数据结构 = 逻辑结构 + 存储结构 + 运算/操作
数据结构: 组织并存储数据以便能够有效使用的一种专门格式。用来反映一个数据的内部构成,即一个数据是由哪些成分数据构成。
逻辑结构: 线性结构 --- 一对一 、 树状结构 --- 一对多 、 网状结构 --- 多对多
存储结构: 顺序存储、链式存储、索引存储、散列存储
顺序表和链表的比较(如果按内容查找两者差不多)
顺序表:按索引查找 查找速度快 删除和添加的速度慢 (因为涉及到了数组大量的移动){ArrayList}
链表: 查找速度慢 删除和添加速度快 {LinkList 双向链表}
哈希表:按内容查找,但不比较,直接算出位置(添加、查询、删除速度快)
主结构为顺序表,每个顺序表的节点在单独引出一个链表
哈希码值:Y = k(x) = x % (哈希表的索引长度) {哈希表的插入}
装填因子 = 表中记录数 / 哈希表长度 (相关文献证明因子在0.5的时候 哈希表性能最优)
因子越小,表中空单元越多,发生冲突的可能性就越小
冒泡排序
(先考虑排序一趟的,而后加循环写多趟的) 一共需要n-1趟
选择排序
(先假设第一个是最小的,和后方每一位相比。如果假设的数不是最小的了即交换下标) arr[minIndex] > arr[i] minIndex = i;
Arrays.sort(); 排序
Arrays.binarySearch(); 二分查找
折半查找(先排序 再查找)1 2 为使用前提
1.表必须是顺序存储结构
2.必须按关键字大小有序排序
int start = 0; //开始下标
int end = arr.length - 1; //结束下标
while(start < end){
int mid = (start + end ) / 2;
if(arr[mid] == key){
return mid;
}elseif(arr[mid] > key){
end = mid -1;
}elseif(arr[mid] < key){
start = mid + 1;
}
return -1; //(没有找到)
}
递归
基本思想就是自己调自己。
1. 调用层次多比循环慢
2.占用大量栈堆,内存耗用多
3.任何能用递归解决的问题 循环都能解决
时间复杂度和空间复杂度
算法:指的是解决程序问题的一组方法
时间复杂度:来区分算法好坏; 时间、速度
空间复杂度:占用内存空间大小来评判
所以通常从时间和空间两个方向去考虑
集合
集合包括(List、set、map)
Collection: 接口储存一组不唯一无序的对象
List: 有序(索引顺序的对象)
set: 唯一、无序
map: 一组键值对、提供key到value的映射(key:唯一、无序。value:不唯一、有序)
泛型
特点:安全、严进、简单、宽出 {限定当前集合、类、方法类型从而达到安全}
& 与运算 有一个 0 返回 0 ,同为 1 返回 1
| 或运算 有 1 为 1 , 全 0 为 0
^ 异或运算 相同为 0 ,不同为 1
~ 按位非运算 取反 0的取反为 -1
>> 右移为除2
>> 左移为乘2 eg:2 x 8 = 2 >> 3
ArrayList(底层是一个 数组)(有序不唯一)
二次扩容会增加百分之五十、原基础长度是10
如果增加了百分之五十不够 则使用目前内容长度作为新数据的长度
优点:遍历、访问速度高。 缺点: 添加、删除速度慢
创建一个ArrayList对象 <> 泛型 必须放的是一个对象类
ArrayList<> arr = new ArrayList(); 定义一个ArrayList集合
增 arr.add() 向集合中 添加数据
输出 arr.get() 索引取单个值,get内书写索引下标
arr.size() 返回的是 集合长度
arr.toString() 集合输出
改 arr.set(2,99) 把索引下标为 2 的数据值改为 99
删 arr.remove(2) 删除下标为 2 的元素(后元素会移动 因此改变下标)
arr.remove(new Integer(22)) 删除内容为22的元素
arr.isEmpty() 判断当前集合是否为空
arr.contains() 判断arr集合里是否包含有无指定元素
arr.sort() 排序输出 从小到大的排序 arr.reverse() 从大到小的排序
LinkedList(底层是一个 双向链表)
对比ArrayList增加的方法
arr.addFirst(); 首增加
arr.addLast(); 尾增加
arr.add(2,99); 中间指定位置增加元素(只是添加节点、不同于ArrayList的大量后移)
arr.removeFirst() 删除第一个元素
arr.removeLast() 删除最后一个元素
arr.getFirst() 获得第一个
arr.getLast() 获得最后一个
ArrayList 和 LinkedList 的使用对比
大量的根据索引查询遍历操作用 ArrayList
较多的添加和删除用 LinkedList、
Map(储存的键值对映射关系,根据key可以找到value)
HashMap:添加快、查询快、删除快、key无序、哈希表储存(底层)
TreeMap:查询速度比List快(按内容查)没有HashMap快、key有序(按照key的大小顺序)、二叉树(红黑树)底层
LinkedMap:使用链表维护次序、key有序(按照key的添加顺序)、哈希表储存(底层)
Map集合的使用
初始内存为16,扩容为2倍数扩容。
个数超过8,自动转为红黑树结构(提高效率)
个数超过8,长度小于6,自动转换为链表
创建一个Map map<Integer,String> map = new HashMap<>();
增 map.put(1,"java01") 给map集合保存 键与值
取 String s = map.get(1) 根据key 取相应的 value
遍历Map:
先获得所有的key,后用get(key)进行value取值
Set<Integer> keys = map.keyset(); // 获得当前集合所有的key
for(Integer k : keys){
System.out.println(map.get(k)); // 遍历集合
}
map集合中的key是唯一的。如果key冲突了 后面的会把前面的覆盖
map.isEmpty 判断是否为空
map = new HashMap<>(); 没有内容,但有内存空间
map = null ; 没有分配内存空间
Set (无序、唯一) 查询、删除、添加速度快
定义一个set集合
set<string> set = new HashSet<>();
增 set.add(); 添加元素 无顺序输出 且有唯一性(同样的元素只能输出一个)
(底层是一个Map)
set<string> set = new LinkedHashSet<>();
跟上方比,多了一个有序(顺序为自然插入的添加顺序)唯一(底层双向链表)
set<string> set = new TreeSet<>();
也是有序的(自然排序的内容数据大小顺序)唯一 (底层为红黑树)
Set集合存对象保证唯一的方式
HashSet、LinkedHashSet 想要保证对象唯一不重复,需要在对象内重写 eq()、hashcode()方法
TreeSet 需要实现comparable接口 implements Comparable<student>{}