学习完单链表之后,瞧着静态链表颇为有趣,于是又动手实现一通。
这次把整个命名空间都放上来啦,惯例把增删改查都练习一遍,感觉今天链表对结构的运用更为巧妙,写起来神清气爽,目前不清楚除了装逼有什么实用价值- -。咳。
简单来说就是用数组结构实现一个单链表,然后就意识到,大概lua用table实现类也是一个道理。
数据的结构分为两种类型,一种是原子类型一种是结构类型,既然类和数组都是结构类型,不如九九归一,大智慧啊!
namespace StaticLists
{
class Program
{
static void Main(string[] args)
{
StaticLinkedList sll = new StaticLinkedList(100);
for (int i = 0; i < 5; i++)
{
sll.ListInsert(sll.GetLength() + 1, i + 1);
}
Console.WriteLine("--------------------------");
Print(sll);
Console.WriteLine();
sll.ListInsert(3, 99);
Console.WriteLine("--------------------------");
Print(sll);
Console.WriteLine();
sll.SetData(4, 10);
Console.WriteLine("--------------------------");
Print(sll);
Console.WriteLine();
Console.WriteLine("--------------------------");
sll.ListDelete(4);
Print(sll);
Console.ReadLine();
}
static void Print(StaticLinkedList sll)
{
int data = 0;
for (int i = 1; i <= sll.GetLength(); i++)
{
sll.GetDate(i,ref data);
Console.Write("num{0}={1}\t",i,data);
}
}
}
public struct StaticNode
{
public int data;
/// <summary>
/// 游标
/// </summary>
public int cur;
}
/// <summary>
/// 静态链表
/// </summary>
/// 数组的第一个原属的cur用来存放备用链表第一个结点的下标
/// 数组的最后一个元素的cur用来存放链表头的下标
public class StaticLinkedList
{
int maxSize;
StaticNode[] staticNodes;
/// <summary>
/// 生成静态链表的时候初始化
/// </summary>
/// <param name="maxSize">链表的最大长度</param>
public StaticLinkedList(int maxSize)
{
this.maxSize = maxSize;
this.staticNodes = new StaticNode[maxSize];
for (int i = 0; i < maxSize - 1; i++)
{
staticNodes[i].cur = i + 1;
}
//staticNodes[maxSize - 1] = new StaticNode();
} /// <summary>
/// 申请结点
/// </summary>
/// <returns>下标</returns>
public int MallocSLL()
{
int i = 0;
if (staticNodes[0].cur != maxSize - 1)
{
i = staticNodes[0].cur;
staticNodes[0].cur = staticNodes[i].cur;
}
return i;
}
/// <summary>
/// 释放节点
/// </summary>
/// <param name="index">释放的下标</param>
public void FreeSLL(int index)
{
staticNodes[index].cur = staticNodes[0].cur;
staticNodes[0].cur = index;
}
public int GetLength()
{
int j = 0;
int i = staticNodes[maxSize - 1].cur;
while (i != 0)
{
i = staticNodes[i].cur;
++j;
}
return j;
}
public bool ListInsert(int index, int data)
{
if (index < 1 || index > GetLength() + 1)
return false;
int j = MallocSLL();
if (j != 0)
{
int k = maxSize - 1;
staticNodes[j].data = data;
for (int i = 1; i <index; i++)//找到第index-1个数
{
k = staticNodes[k].cur;
}
staticNodes[j].cur = staticNodes[k].cur;
staticNodes[k].cur = j;
return true;
}
return false;
}
public void ListDelete(int index)
{
//觉得返回值麻烦就换了个方法写。
if (index < 1 || index > GetLength())
{
Console.WriteLine("下标溢出");
}
else
{
int k = maxSize - 1;
for (int i = 1; i < index; i++)
{
k = staticNodes[k].cur;
}
int num = staticNodes[k].cur;
staticNodes[k].cur = staticNodes[num].cur;
FreeSLL(num);
Console.WriteLine("删除成功");
}
}
public void SetData(int index,int data)
{
if(index<1 || index>GetLength())
Console.WriteLine("下标溢出");
else
{
int k = maxSize - 1;
for (int i = 1; i <= index; i++)
{
k = staticNodes[k].cur;
}
staticNodes[k].data = data;
}
}
public bool GetDate(int index,ref int data)
{
if (index < 1 || index > GetLength())
{
Console.WriteLine("下标溢出");
return false;
}
else
{
int k = maxSize - 1;
for (int i = 1; i <= index; i++)
{
k = staticNodes[k].cur;
}
data = staticNodes[k].data;
return true;
}
}
}
}