一.ArrayList
1.1.前言
在使用这些方法之前,我们可以想一下,如果这些方法让我们自己实现它的功能我们应该怎么写呢?
1.2 自己写的add:功能
isfull方法是来判断数组是否满了,grow是来扩容的,this.arr是需要扩容的数组,2*arr.length是扩容的大小。
通过数组来存放你add方法的值。
这个是可以填自己指定的位置。
checkpos方法是防止错误输入的。
而checkadd是我们自己写的一个异常。
我们输入一个越界的。
就会报出异常。
1.3 自己写的contains方法
通过遍历数组的形式来找是否存在某个值。
1.4 自己写的indexof方法
这个方法数用来等到你想要的元素的下标的。
通过isempty方法来判断数组是否为空。
isemptyexption是我们写的自定义空值异常的方法。
1.5 自己写的get方法
返回某个下标的元素。
1.6 自己写的set方法
通过输入你要改的下标和值,就可以了。
1.7 自己写的remove方法
通过上面的indexof方法找到你要修改的元素的下标,在通过数组覆盖的方式移除那个值。
1.8 自己写的size方法
放回数组的长度。
1.9 自己写的clear方法
该方法的作用是清屏的。
1.10 自己写的display方法
遍历数组。
这些方法是我们通过自己对这些方法的表层理解来自己写的,实际内部原理很复杂,这可以帮助我们简单理解一下。
2.1 Arraylist的简介
在集合框架中,ArrayList是一个普通的类,实现了List接口,具体框架图如下:
说明:
2.2 Arraylist的使用
2.2.1 Arraylist的构造方法
2.3 Arraylist常用的一些方法
2.3.1 add方法
通过list输出结果说明Arraylist也有自己的toString的方法,还要两个可以自己试一下,很简单。
2.3.2 addall方法
插入的对象得是Arraylist对象。
2.3.3 get方法
跟数组一样就是拿元素的。
2.3.4 set方法
修改已经存在的值,无法建立新的值。
注意:
set 方法用于修改指定索引位置的元素,不能用于创建新的元素。如果指定的索引位置超出了当前列表的范围,就会抛出 IndexOutOfBoundsException 异常。
如果您想要向列表中添加新元素,应该使用 add 方法。
其他的方法大家感兴趣都可以自己试试,我就不一一列举了。
2.2.5 remove方法
它有两种用法,如图所示,一种是输入元素的索引来删除对象,一种则是通过内容删除对象。
2.4 Arraylist的遍历
第一种遍历
跟数组一样。
第二种遍历借助foreach遍历
第三种通过迭代器来遍历
如图所示,it表示的是一个迭代器对象。
hasnext方法
它的作用就是让光标移动到下一个的,并判断下一个位置是否存在元素,存在返回true,没有返回false。
开始在最上面,你可以理解为光标在下表为-1的位置当然它是不存在-1的,就是0之前的那个位置。进去一次,向后移动一个位置。
next方法
获取当前位置的元素并返回。
2.4 Arraylist的自动扩容机制
下面的代码有问题吗?
它是怎么进行扩容的?
在 Java 中,ArrayList
的底层使用了一个数组来存储元素。当使用 add
方法添加元素并且当前数组容量不足时,ArrayList
会自动进行扩容操作。
默认情况下,创建一个 ArrayList
对象时,其初始容量为 10 。当添加元素导致数组已满时,扩容的策略通常是将当前容量增加约 50% 。也就是说,如果当前容量为 n
,扩容后的新容量大致为 n + n / 2
。
具体的扩容过程大致如下:
- 创建一个新的更大容量的数组。
- 将原数组中的元素复制到新数组中。
- 将新添加的元素放入新数组的合适位置。
这种自动扩容的机制为开发者提供了便利,使得在使用 ArrayList
时无需过多关注底层数组容量的管理,但也需要注意频繁扩容可能会影响性能,特别是在预计会存储大量元素的情况下,可以在创建 ArrayList
时指定一个合适的初始容量。
如何手动设置 ArrayList 的初始容量?
ArrayList 在扩容时,复制元素的效率如何?
除了 ArrayList,还有哪些集合类提供了自动扩容的功能?
2.5 扩充的知识
接口对象
Arraylist实现的还要一些接口,也可以通过接口来实例化对象。
它俩的区别:
1. 类型声明的明确性:
在第一种方式中,明确声明了变量 list
的类型为 ArrayList
。
在第二种方式中,声明变量 list1
的类型为更通用的接口 List
,实际创建的对象是 ArrayList
。
2.灵活性:
当使用 List
接口类型进行声明(如第二种方式)时,如果后续因为需求变更需要将实现类从 ArrayList
更换为其他实现了 List
接口的类(如 LinkedList
),代码修改的范围较小,只需要修改创建对象的那一行代码,而使用该变量的其他代码无需修改。
因为 ArrayList
实现了 List
接口中定义的所有方法,无论通过 ArrayList
类型声明还是通过 List
接口类型声明并创建 ArrayList
对象,都能够调用 List
接口中定义的那些方法。
sublist方法
接收值是List类型的。
表示把索引为[0,2)的内容给List<Integer> l这个对象,左闭右开的形式。
结果
迭代器知识的扩充
我们上面也讲到了通过迭代器也可以遍历Arraylist对象的内容
接下来我们再讲一下ListIterator这个接口。
它比Iterator多了几个方法,我们举出几个常用的。
它和上面的hasnext方法不同的是,它是从后往前遍历输出的,hasnext是从前往后遍历输出的。
二维List
List中套上一个List。
赋值方式
第一种
直接给这个类似二维的一个List<Integer>对象。
结果
第二种
通过Arrays的asList方法给这个二维的赋值。
结果
遍历方法
第一种
跟二维数组差不多一样
结果
这个Arrays.aslist方法不能和add方法联合使用。
什么意思呢?
这样没有任何问题。
这样就有问题了。
报错了。
你可以理解为,当你用aslist赋值完成之后,这个数组的大小就锁死了,无法添加元素。
注意:
list.add(Arrays.asList(val1 + val)) 这种方式不是在已有内层列表的合适位置添加值,而是直接向外层的 list 中添加一个新的内层列表。
在 List<List<Integer>> list 中,list 是外层列表。
而 list 中的每个元素,比如 list.get(0) 、list.get(1) 等,这些元素本身也是一个 List<Integer> ,它们被称为内层列表。
简单理解就是每一行是一个外层,每一行中的值是内层。
第二种
通过for-each语句遍历。跟数组差不多一样
结果
第三种
通过迭代器的方式遍历。
先通过第一层while循环取出我们想要输出的。
然后通过第二层循环进行输出。
结果
第四种
和第三种基本一样,只是把第三种的Iterator<Integer> list = listInteger.next().listIterator();拆开来写了。
2.6 练习
第一个练习
去除str中的str1所包含的字母。
例如:str=“abcda” , str1=“ab”。
去除之后就是“cd”。
三种作法。
第一种
通过把字符串变成字符数组,然后利用字符数组的形式进行操作。
第二种方法
第三种利用我们所学的数据结构
为什么会报错呢?
CharSequence表示要传入一个字符串形式,而不是字符形式。
怎么解决呢?
如下图
通过这个想法来解决。
如下图:
这样就能把字符变成字符串的形式了。
第二个练习:杨辉三角
要求:通过我们学的打印出来杨辉三角。
这是第一部分,创建一个二维的List对象,然后放入一个对象list2,他就会把杨辉三角的第一行完成。
a是控制杨辉三角的行数的。
第一层for循环,创建一个list1对象,先add(1),是完成每次杨辉三角的第一列.
用一个list3对象来接收一下list的内层,通过下面的两个int类型的变量来接收值。
把值给到list1对象中,就得到了这一部分内容。
最后的list1.add(1)是完成每一行的最后一个元素的。
最后把全部的值给到list。
通过我们上面教的方法按照要求打印出来。
就是这个效果了。
第三个练习(扑克牌)
3.1 买牌
要求就是先得到一副扑克牌才行。
这是我们的牌库。
String数组来表示花色,通过buycard方法来得到扑克牌,先创建一个Arratlist动态数组,一共52张牌(不含大小王),13个数字和4个花色,通过for循环来控制。
通过rank拿到数字,s拿到花色,实例化对象放到动态数组中,最后返回。
结果:
后面太多了,没有截完图。
买完牌之后我们就可以开始玩了。
3.2 打牌
打牌之前我们要洗牌。
接下来我们就写一个洗牌的操作。
3.2.1 洗牌
int index = rd.nextInt(i);
这段代码通常是从一个随机数生成器 rd
中获取一个介于 0
(包含)和 i
(不包含)之间的随机整数,并将其赋值给变量 index
。
通过生成随机数和你的i位置的值交换一下。
洗完牌之后,我们就要开始发牌了。
3.2.2 发牌
创建三个玩家list,list1,list2,通过if语句控制发牌,先发一号玩家。
也可以这样发牌,通过一个二维动态数组,把三个玩家传进去,然后通过双层for循环,第一层代表每个玩家有多少个牌,第二层代表玩家的数量。
通过remove来得到你去除的对象,他会返回一个card类型的值,然后通过card类型的变量来接收这个值,每次去除完成之后,后一个元素的索引-1,所以就是按照顺序,你要拿的牌的索引一直为0;
通过冒泡排序来整理牌的顺序,从小到大。
这个是用来判断二号玩家要不要地主,不要就问下一家,也就是三号玩家。
这个是用来判断三号玩家要不要地主,不要就问下一家,也就是一号玩家。
这个是用来判断一号玩家要不要地主,不要就问下一家,也就是二号玩家。
只要两家玩家不要,第三家必须要,有种强制的感觉。
在整理一下牌。
这个的作用就是来生成一个随机数,a是来代表花色的,b是来代表牌的大小的,有三张地主。这是我自己随便写的一个东西,和现实的斗地主可能不同。
最后:结束语
感谢大家的查看,希望可以帮助到大家,做的不是太好还请见谅,其中有什么不懂的可以留言询问,我都会一一回答。 感谢大家的一键三连。