目录:
正文:
1. 泛型,就是通用的类型。它是设计上的术语。(不关注数据类型,只关注算法逻辑)
通用链表 GenericList
GenericList :该类封装了链表结构,可以适用于任何类型作为节点类型。
示例:
GenericList list = new GenericList();
list.add( new Student(1, "shao", "13810012345"));
list.add( new Student(2, "wang", "15290908889"));
list.add( new Student(3, "li", "13499230340"));
设计思路
1 不限制节点类型,所以用Object作为节点的类型
class GenericNode
{
Object value; // 可以是任何类型
GenericNode next;
//只是一个引用,相当于c中的指针,并不是GenericNode对象
}
2 迭代器
使用Iterator进行链表的遍历
代码:
package my;
public class GenericList
{
// 通用节点类型
private static class GenericNode
{
Object value;
GenericNode next;
}
// 固定头节点
private GenericNode head = new GenericNode();
public GenericList()
{
}
// 添加一个对象
public void add ( Object value )
{
// 找到末节点
GenericNode tail = head;
while( tail.next != null)
tail = tail.next;
// 附加到末尾
GenericNode node = new GenericNode ();
node.value = value;
tail.next = node;
}
// 长度
public int length()
{
int count = 0;
GenericNode m = head.next;
while( m != null)
{
count += 1;
m = m.next;
}
return count;
}
// 获取迭代器
public Iterator getIterator()
{
Iterator iter = new Iterator();
iter.node = this.head;
return iter;
}
//
public static class Iterator
{
private GenericNode node;
// 是否还有下一节点
public boolean hasNext()
{
return node.next != null;
}
// 获取下一节点的值
public Object next()
{
Object value = node.next.value;
node = node.next;
return value;
}
}
}
2. 泛型规范的使用方法
泛型的定义
泛型一般用于描述一种通用的算法、数据结构,对象类型其实并不关心。所以,可以用一个代号 T 来代表目标类型。
在Java语言里,泛型的规范写法:
public class Sample
{
}
在类的定义里,T代表一个通用的类型,把T称为类型参数
泛型的使用
正规写法下,使用泛型应指定类型参数
Sample
sa = new Sample ();
注:我们在实际工程中都是使用JDK里现成的泛型,不需要自己写泛型。本章能理解原理即可。
public class Sample
{ T value; public void setValue(T value) { this.value = value; } public T getValue() { return this.value; } }
3. 数组链表 ArrayList
常用的泛型
工作中最常用到的两个泛型:
List , ArrayList
Map, HashMap
注:通常我们是不需要自己写泛型的,因为JDK自带的这两个泛型已经足够用了。
ArrayList
ArrayList : 数组链表。既像数组,又像链表。
示例:
ArrayList
ArrayList
ArrayList
注:不能用ArrayList
添加、插入
add( ) 的时候可以指定插入位置。默认附加到末尾。
ArrayList list = new ArrayList<>();
list.add( new Student(1, "shao", "13810012345"));
遍历(像数组一样遍历, 像链表一样遍历)
像数组一样遍历
for(int i=0; i iter = list.iterator();
while(iter.hasNext())
{
Student s = iter.next();
System.out.println(s);
}
删除(像数组一样删除, 像链表一样删除)
像数组一样删除
list.remove( index )
像链表一样删除 (更高效)
Iterator iter = list.iterator();
while(iter.hasNext())
{
Student s = iter.next();
if(s.id == 2)
{
iter.remove(); // 删除
}
}
排序
排序时,需要传一个Comparator对象,它是一个接口。
所以创建一个匿名类对象,
Collections.sort(list, new Comparator() {
@Override
public int compare(Student a, Student b)
{
if(a.id < b.id) return -1;
else if(a.id > b.id) return 1;
else return 0;
}
});
重写compare方法,其返回值决定了a,b的先后顺序:
如果<0,则a在b之前
如果>0,则a在b之后
如果==0,则a,b相等
小结:
ArrayList是最常用的一种泛型
介绍了ArrayList的基本使用方法
按数组方式更简单(开发效率高)
按链表方式更高效(运行效率高)
通常情况下,我们追求的是更简单、而不是更高效
4. 哈希表 HashMap
Map与 HashMap
Map : 映射表 ( 抽象类)
HashMap : 哈希映射表,是Map的一个实现
HashMap的存储:key ó value
• 键值对
• 每个 value 都有一个唯一的 key
• 通过 key 可以迅速找到 value
HashMap的创建
其中,链表方式更高效,参考 数据结构与算法
创建Map时,要指定key和value的类型
示例:
( 学号 ó 学生)
• HashMap
HashMap 常见操作
• 添加
• 查找
• 删除
• 遍历
1 创建 Map
以学号作为 Key
HashMap map = new HashMap();
2 添加
map.put( 1, new Student(1, "shao", "13810012345"));
map.put( 2, new Student(2, "wang", "15290908889"));
map.put( 3, new Student(3, "li", "13499230340"));
连续多次put时,如果key值已经存在,则覆盖旧的值。
3 查找
Student s = map.get(1); //键值 key
if( s != null )
{
System.out.println("找到:" + s);
}
4 删除
删除对象时,指定要删除的key值:
map.remove(3);
删除所有
map.clear();
5 遍历所有的key和value
通常情况下,map是不遍历的。偶尔需要遍历。
// 遍历所有的key
Set keys = map.keySet();
for(Integer k : keys)
{
System.out.println("key: " + k);
}
// 遍历所有的value
for(Student v : map.values())
{
System.out.println("value: " + v);
}
问题1: 以姓名作为 Key ?
HashMap map = new HashMap();
map.put( "shao", new Student(1, "shao", "13810012345"));
map.put( "wang", new Student(2, "wang", "15290908889"));
map.put( "li", new Student(3, "li", "13499230340"));
必须保证姓名没有重复的。
以姓名作为 key
哈希查找更快 hash查找就是你在教室门口喊一声小明,你妈喊你回家吃饭了,然后小明听到了, 立马站起.
遍历查找就是小明 背着她妈妈在网吧, 你喊他,他装作没听见, 你要按着网吧电脑编号到位置上一个个的找.!
当查找非常频繁时,用HashMap以提高运行效率
总结:
List , ArrayList
Map, HashMap
通常我们是不需要自己写泛型的,因为JDK自带的这两个泛型已经足够用了。
掌握两个泛型的使用.
当查找非常频繁时,用HashMap以提高运行效率
至于hashmap的查找原理, 自己去看算法导论, emmmm(笔者其实自己也不知道, emmmm我会学的!!! 学完再来写!!. )
现在算算, 还有java命令行, 文件操作, 反射, 线程并发没写, 这些都是我学的比较懵的, 这段时间不打算更. 过段时间学精了再更, 所以下一步更javaEE.