容器的分类
泛型的概念:
泛型相当于占位符,告诉编译器调用泛型的时候必须传入实际类型
package 容器;
public class 泛型 {
public static void main(String[] args) {
MyCollection<String> mc=new MyCollection<String>();//实参
mc.set("高淇",0);
//mc.set(8888,1);
//Integer a=(Integer)mc.get(1);
String b=(String) mc.get(0);//泛型之后不用强制转换
}
}
class MyCollection<E>{//形参
Object[] objs=new Object[5];
public void set(E e,int index){
objs[index]=e;
}
public E get(int index){
return (E)objs[index];
}
}
TestList
remove移除时是移除地址 对象还在
package 容器;
import java.util.*;
//测试Collection接口中的方法
public class TestList {
public static void main(String[] args) {
Collection<String> c=new ArrayList<String>();
System.out.println(c.size());
System.out.println(c.isEmpty());
c.add("高老大");
c.add("高老二");
System.out.println(c);
System.out.println(c.size());
System.out.println(c.contains("高老二"));//是否包含高老二
System.out.println(c.contains("高老五"));
Object[] objs=c.toArray();//转换成Object数组
System.out.println(objs);
c.remove("高老二");
System.out.println(c);
c.clear();//移除所有元素
System.out.println(c.size());
}
}
package 容器;
import java.util.*;
public class TestList2 {
public static void main(String[] args) {
test02();
}
public static void test01() {}
public static void test02(){
List<String> list01=new ArrayList<>();
//ArrayList<String> list2=new List<>();
list01.add("aa");
list01.add("bb");
list01.add("cc");
List<String>list02=new ArrayList<>();
list02.add("aa");
list02.add("dd");
list02.add("ee");
System.out.println("list01:"+list01);
//list01.addAll(list02);
//list01.removeAll(list02);//删除相同的部分
list01.retainAll(list02);
System.out.println("list01:"+list01);
System.out.println(list01.containsAll(list02));
}
}
package 容器;
import java.util.ArrayList;
import java.util.List;
public class TestList3 {
public static void main(String[] args) {
test03();
}
public static void test03(){
List<String>list =new ArrayList<>();
list.add("A");
list.add("B");
list.add("C");
System.out.println(list);
list.add(2,"高淇");
System.out.println(list);
list.remove(2);
list.set(2,"高老二");
System.out.println(list);
System.out.println(list.get(2));
list.add("D");
list.add("C");
list.add("B");
list.add("A");
System.out.println(list);
System.out.println(list.indexOf("B"));//不存在返回-1
System.out.println(list.lastIndexOf("B"));//从右向左第一个元素
}
}
package MyArrayList;
//手写ArrayList
//增加set get remove
public class SxtArrayList3<E> {
private Object[] elementData;
private int size;
private static final int DEFALT_CAPACITY=10;
public SxtArrayList3(){
elementData=new Object[DEFALT_CAPACITY];
}
public SxtArrayList3(int capacity){
if(capacity<0){
throw new RuntimeException("容器的容量不能为负数");
}else if(capacity==0){
elementData=new Object[DEFALT_CAPACITY];
}else {
elementData = new Object[capacity];
}
}
public void add(E element){
//扩容
if(size ==elementData.length) {
Object[] newArray = new Object[elementData.length + (elementData.length >> 1)];//10-->10+10/2 +优先级高于>>
//拷贝
System.arraycopy(elementData, 0,newArray,0,elementData.length );
elementData=newArray;
}
elementData[size++]=element;
}
public E get(int index){
checkRange(index);
return (E)elementData[index];
}
public void set(E element,int index) {
//索引合法判断[0,size)
checkRange(index);
elementData[index] = element;
}
public void checkRange(int index){
if (index < 0 || index >size - 1) {
throw new RuntimeException("索引不合法"+index);//抛出异常
}
}
public void remove(E element){
//element 将它和所有元素挨个比较 获得第一个比较为true的 返回
for(int i=0;i<size;i++){
if(element.equals(get(i))){//容器中所有比较都用的是equals而不是==
//将该元素从此处移除
remove(i);
}
}
}
public void remove(int index){
int numMoved=elementData.length-index-1;
if(numMoved>0) {//移动的位置大于0
System.arraycopy(elementData, index + 1, elementData, index, numMoved);
}
elementData[--size]=null;
}
public int size(){
return size;
}
public boolean isEmpty(){
return size==0?true:false;
}
//重写toString方法
@Override
public String toString() {
StringBuilder sb=new StringBuilder();
sb.append("[");
for(int i=0;i<size;i++){
sb.append(elementData[i]+",");
}
sb.setCharAt(sb.length()-1,']');//最后一个换成]号
return sb.toString();
}
public static void main(String[] args) {
SxtArrayList3 s1=new SxtArrayList3();
for(int i=0;i<40;i++){
s1.add("gao"+i);
}
s1.set("dddd",39);
System.out.println(s1);
System.out.println(s1.get(39));
s1.remove(3);
System.out.println(s1);
s1.remove("gao11");
System.out.println(s1);
System.out.println(s1.size());
System.out.println(s1.isEmpty());
}
}
手写链表
package 链表;
public class Node {
Node previous;//上一个节点
Node next;//下一个节点
Object element;//元素数据
public Node(Node previous,Node next,Object element){
super();//不写默认会加
this.previous=previous;
this.next=next;
this.element=element;
}
public Node(Object obj) {
super();
this.element=obj;
}
}
package 链表;
//自定义一个链表
//链表增加删除速度快 查找速度慢
public class LinkedList<E> {
private Node first;
private Node last;
private int size;
public Node getNode(int index){
Node temp = null;
if (index < (size >> 1)) {//size>>1相当于除以2
temp = first;
for (int i = 0; i < index; i++) {
temp = temp.next;
}
} else {
temp = last;
for (int i = size - 1; i > index; i--) {
temp = temp.previous;
}
}
return temp;
}
public void add(int index,E e){
Node newNode=new Node(e);
Node temp=getNode(index);
if (temp!=null){
Node up=temp.previous;
up.next=newNode;
newNode.previous=up;
newNode.next=temp;
temp.previous=newNode;
}
}
public void remove(int index){
Node temp=getNode(index);
if(temp!=null){
Node up=temp.previous;
Node down=temp.next;
if(up!=null){
up.next=down;
}
if(down!=null) {
down.previous = up;
}
//被删除的元素是第一个时
if(index==0){
first=down;
}
//被删除的元素是最后一个时
if(index==size-1){
last=up;
}
size--;
}
}
private void checkRange(){
}
public Object get(int index) {
if (index < 0 || index > size - 1) {
throw new RuntimeException("索引数字不合法" + index);
}
Node temp=getNode(index);
return temp!=null?(E)temp.element:null;
}
public void add(Object obj){
Node node =new Node(obj);
if(first==null){
first=node;
last=node;
}else{
node.previous=last;
node.next=null;
last.next=node;
last=node;
}
size++;
}
public String toString(){
StringBuilder sb=new StringBuilder("[");
Node temp=first;
while(temp!=null){
sb.append(temp.element+",");
temp=temp.next;
}
sb.setCharAt(sb.length()-1,']');
return sb.toString();//将StringBuilder变为String
}
public static void main(String[] args) {
LinkedList<String> list=new LinkedList<>();
list.add("a");
list.add("b");
list.add("c");
list.add("d");
list.add("e");
list.add("f");
System.out.println(list);
list.remove(3);
System.out.println(list);
list.remove(0);
System.out.println(list);
list.remove(3);
System.out.println(list);
list.add(3,"老高");
System.out.println(list);
}
}
Vector向量
package Vector;
import java.util.List;
import java.util.Vector;
public class TestVector {
public static void main(String[] args) {
List<String> list=new Vector();
}
}
package 容器;
import java.util.HashMap;
import java.util.Map;
public class TestMap2 {
public static void main(String[] args) {
Employee e1=new Employee(1001,"高淇",50000);
Employee e2=new Employee(1002,"小二",5000);
Employee e3=new Employee(1003,"小屋",6000);
Employee e4=new Employee(1001,"小六",7000);
Map<Integer,Employee> map=new HashMap<>();
map.put(1001,e1);
map.put(1002,e2);
map.put(1003,e3);
Employee emp=map.get(1001);
System.out.println(emp.getName());
System.out.println(map);
}
}
//雇员信息
class Employee{
private int id;
private String name;
private double salary;
public Employee(int id,String name,double salary){
super();
this.id=id;
this.name=name;
this.salary=salary;
}
public String toString(){
return "id"+id+"name:"+name+"薪水:"+salary;
}
public String getName(){
return this.name;
}
}
手写HashMap
package HashMap;
import java.util.HashMap;
public class HashMapfanxing<K,V> {
Node3[] table;//位桶数组
int size;//存放键值对的个数
public HashMapfanxing(){
table=new Node3[16];//长度一般定义为2的整数
}
public V get(K key){
int hash = myHash(key.hashCode(), table.length);//算出对于的hash值
V value=null;
if(table[hash] != null) {
Node3 temp=table[hash];
while(temp != null){
if(temp.key.equals(key)){//如果相等 说明找到了键值对 返回对应的value
value=(V)temp.value;
break;
}else{
temp=temp.next;
}
}
}
return value;
}
public void put(K key,V value){
//如果要完善要考虑数组扩容的问题
//定义了新的节点对象
Node3 newNode=new Node3();
newNode.hash=myHash(key.hashCode(),table.length);
newNode.key=key;
newNode.value=value;
newNode.next=null;
Node3 temp=table[newNode.hash];
Node3 iterLast=null;//正在遍历最后一个元素
boolean keyRepeat = false;
if(temp == null){
//此处数组为空则直接将新节点放进去
table[newNode.hash] = newNode;
size++;
}else{
//如果不为空 则遍历对应链表
while(temp != null){
//判断key如果重复 则覆盖
if(temp.equals(key)){
keyRepeat = true;
System.out.println("key重复了!");
temp.value=value;//只是覆盖了value即可 其他的hash key next保持不变
break;
}else{
//key不重复 则遍历下一个
iterLast = temp;//iterLast存放链表最后一个对象
temp=temp.next;
}
}
if(!keyRepeat){//如果没有键值重复
iterLast.next=newNode;
size++;
}
}
}
public String toString(){
StringBuilder sb=new StringBuilder("{");
//遍历bucket数组
for(int i=0;i<table.length;i++){
Node3 temp=table[i];
//遍历链表
while(temp!=null){
sb.append(temp.key+":"+temp.value+',');
temp=temp.next;
}
}
sb.setCharAt(sb.length()-1,'}');
return sb.toString();
}
public static void main(String[] args) {
HashMapfanxing<Integer,String> m=new HashMapfanxing<>();
m.put(10,"aa");
m.put(20,"bb");
System.out.println(m.get(30));
}
public static int myHash(int v,int length){
System.out.println("hash in myHash:"+(v&(length-1)));//直接位运算 效率高
System.out.println("hash in myHash:"+(v%(length-1)));//取模运算 效率低 两者作用一样 值不一样
return v&(length-1);
}
}
手写HashSet
package Set;
import java.util.HashMap;
//手动实现一个HashSet
public class MyHashSet {
HashMap map;
private static final Object PRESENT=new Object();
public MyHashSet(){
map=new HashMap();
}
public int size(){
return map.size();
}
public void add(Object o){
map.put(o,PRESENT);
}
@Override
public String toString() {
StringBuilder sb=new StringBuilder();
sb.append("[");
for(Object key:map.keySet()){
sb.append(key+",");
}
sb.setCharAt(sb.length()-1,']');
return sb.toString();
}
public static void main(String[] args) {
MyHashSet set=new MyHashSet();
set.add("aaa");
set.add("bbb");
set.add("ccc");
System.out.println(set);
}
}