数组
数组是存储相同类型元素的固定大小的顺序集合
数组定义形式:数据类型[] 数组名
数组的几种定义方法:
int[] a1 = { 1, 2, 3 };
int[] a2 = new int[3] { 1, 2, 3 };
int[] a3 = new int[] { 1, 2, 3 };
int[,] a4 = new int[,] { { 1, 2 }, { 3, 4 } };
int[,] a5 = new int[2, 2] { { 1, 2 }, { 3, 4 } };
C#内置的一些可对数组使用的函数:
int[] array = { 1, 2, 3, 4, 5, 9, 10, 6 };
foreach (int item in array)
{
Console.WriteLine(item);
}
//数组反转
Array.Reverse(array);
foreach (int item in array)
{
Console.WriteLine(item);
}
//数组排序
Array.Sort(array);
foreach (int item in array)
{
Console.WriteLine(item);
}
动态数组(ArrayList)
动态数组:可自动调节数组的大小
动态数组的应用:
ArrayList al = new ArrayList();
Console.WriteLine("容量大小为{0},当前数据长度为{1}", al.Capacity, al.Count);
al.Add(1);
Console.WriteLine("容量大小为{0},当前数据长度为{1}", al.Capacity, al.Count);
al.Add(1);
al.Add(1);
al.Add(1);
al.Add(1);
Console.WriteLine("容量大小为{0},当前数据长度为{1}", al.Capacity, al.Count);
al.Add(true);
al.Add("abc");
al.Add(3.14);
Test t = new Test();
al.Add(t);
Console.WriteLine("容量大小为{0},当前数据长度为{1}", al.Capacity, al.Count);
foreach (var item in al)
{
Console.WriteLine(item);
}
Array这类动态数组会导致装箱和拆箱操作。那什么是装箱和拆箱呢?
装箱与拆箱
装箱与拆箱
将所有的数据的都作为了object去处理
装箱:从值类型转换到引用类型
拆箱:从引用类型转换到值类型
一定只有经过装箱的对象才会有拆箱
装箱与拆箱的原理
装箱的原理:
1.分配堆区内存(值类型数据大小+指针大小)
2.将值类型数据拷贝到分配的堆区内存中
3.将堆区的内存地址返回
拆箱的原理:
1.获取堆区中的属于值类型的地址
2.将堆区中的值类型数据拷贝到栈区中的值类型实例中
性能损耗
1.装箱时,需要分配内存,创建新的对象
2.拆箱时,需要释放内存
装箱与拆箱的案例
int num = 100;
object obj = num;//装箱
Console.WriteLine(obj);
int a = (int)obj;//拆箱
Console.WriteLine(a);
既然这类动态数组创建有额外的开销的话,那么有没有不需要拆箱装箱的动态数组呢?
动态数组(List)
区别于C++的是List在C#中不再是链表而是动态数组,List是泛型
List运用实例:
List<int> list = new List<int>();
Console.WriteLine("容量大小为{0},当前数据长度为{1}", list.Capacity, list.Count);
list.Add(123);
Console.WriteLine("容量大小为{0},当前数据长度为{1}", list.Capacity, list.Count);
list.Add(789);
list.Add(45);
list.Sort();
foreach (int item in list)
{
Console.WriteLine(item);
}
双向链表(LinkedList)
LinkedList运用实例:
LinkedList<int> ll = new LinkedList<int>();
ll.AddFirst(1);
ll.AddFirst(2);
ll.AddLast(3);
foreach (int item in ll)
{
Console.WriteLine(item);
}
LinkedListNode<int> curentNode = ll.Find(1);//查找到数字1所在的位置
ll.AddAfter(curentNode, 4);
foreach (int item in ll)
{
Console.WriteLine(item);
}
ll.AddBefore(curentNode, 5);
foreach (int item in ll)
{
Console.WriteLine(item);
}
ll.Remove(5);
foreach (int item in ll)
{
Console.WriteLine(item);
}
以上就是C#中的线性容器了,那么讲到线性容器肯定得讲到它们各自的特点:
各类线性容器的特点
数组:
1.声明数组时,必须指定数组的大小 2.数组的插入和删除数据比较麻烦,但是查询比较快
ArrayList:
可以存储任意类型数据,但是会带来装箱与拆箱的操作
List:
声明时指定了数据类型,避免了装箱与拆箱,能够自动扩容
LinkedList:
双向链表,插入和删除数据比较快,但是查询比较慢
栈与队列
栈与队列的特点: 栈:先进后出
队列:先进先出
栈与队列的运用实例:
//栈
Stack<int> stack = new Stack<int>();
Console.WriteLine("当前数据长度为{0}", stack.Count);
stack.Push(1);//入栈
stack.Push(2);//入栈
Console.WriteLine("当前数据长度为{0}", stack.Count);
int b = stack.Pop();//出栈,并且将栈顶元素移除
Console.WriteLine(b);
int c = stack.Peek();//出栈,不移除栈顶元素
Console.WriteLine(c);
Console.WriteLine("当前数据长度为{0}", stack.Count);
//队列
Queue<int> queue = new Queue<int>();
Console.WriteLine("当前数据长度为{0}", queue.Count);
queue.Enqueue(1);//入队
queue.Enqueue(2);//入队
Console.WriteLine("当前数据长度为{0}", queue.Count);
int d = queue.Dequeue();//出队,并且将队头元素移除
Console.WriteLine(d);
int e = queue.Peek();//出队,不移除队头元素
Console.WriteLine(e);
Console.WriteLine("当前数据长度为{0}", queue.Count);
哈希表与字典
哈希表与字典的存在形式:
哈希表:键值对形式存储
哈希冲突:不同的键值对在哈希表计算中得到的相同的哈希值
1.链地址法
2.开放寻址法
字典:键值对形式存储
哈希表与字典的异同:
字典与哈希表区别:
相同点:
1.都是键值对形式存在,且键是唯一的,值是不唯一的,都是无序的键值对
2.存储的数据个数不受限制
3.方法高度相似
不同点:
1.键值对的类型不一样,哈希表是任意类型,字典是指定类型
2.命名空间不一样 哈希表System.Collections,字典System.Collections.Generic
3.限制类型不同,字典存储数据时限制类型,哈希表是存储任意类型
4.性能不同,哈希表存在装箱与拆箱,字典不存在装箱与拆箱
哈希表与字典的运用实例:
//哈希表
Hashtable ht = new Hashtable();
ht.Add("1", "a");
ht.Add("2", true);
ht.Add("b", false);
Console.WriteLine("当前数据长度为{0}", ht.Count);
foreach (var item in ht.Keys)
{
Console.WriteLine(item);
}
foreach (var item in ht.Values)
{
Console.WriteLine(item);
}
foreach (DictionaryEntry item in ht)
{
Console.WriteLine("key={0},value={1}", item.Key, item.Value);
}
//删除元素
ht.Remove("b");
foreach (DictionaryEntry item in ht)
{
Console.WriteLine("key={0},value={1}", item.Key, item.Value);
}
//清空哈希表
ht.Clear();
Console.WriteLine("当前数据长度为{0}", ht.Count);
//字典
Dictionary<int, string> dic = new Dictionary<int, string>();
dic.Add(1, "a");
dic.Add(2, "b");
dic.Add(3, "b");
dic.Add(4, "b");
Console.WriteLine("当前数据长度为{0}", dic.Count);
dic.Remove(2);
Console.WriteLine("当前数据长度为{0}", dic.Count);
foreach (int item in dic.Keys)
{
Console.WriteLine(item);
}
foreach (string item in dic.Values)
{
Console.WriteLine(item);
}
foreach (var item in dic)
{
Console.WriteLine(item);
}
foreach (KeyValuePair<int, string> item in dic)
{
Console.WriteLine(item);
}
//查找字典中是否有某个元素
string f = "";
if (dic.TryGetValue(2, out f))
{
Console.WriteLine(f);
}
学习总结
以上就是C#的学习笔记了,希望对你过来解惑的你有一点点帮助。