数据结构——C#实现泛型单链表

1.单链表功能速览

功能方法返回值备注
获取链表长度GetLength()int返回链表长度
清空链表Clear()void
判断链表是否为空IsEmpty()bool
添加元素Add(T item)void在链表尾添加元素
在指定位置插入元素Insert(T item,int index)void插入的元素就是第index位
删除指定位置元素Delete(int index)T
索引器this[int index]T类似数组的索引器
获取指定位置的值GetEle(int index)T以位取值
获取值所在的位置Locate(T value)int以值取位
打印输出单链表MToString()void打印链表

2.主要功能的设计简图

(1)元素的插入

(2)元素的删除

3.单链表结点类

/// <summary>
/// 单链表的结点
/// </summary>
/// <typeparam name="T"></typeparam>
class MyNode<T>
{
    T data;//数据域
    MyNode<T> next;//指针域,用来指向下一个元素
    public T Data
    {
        get { return data; }
        set { data = value; }
    }
    //MyNode的各种构造函数
    public MyNode<T> Next
    {
        get { return next; }
        set { next = value; }
    }
    public MyNode()
    {
        data = default(T);
        next = null;
    }
    public MyNode(T value)
    {
        data = value;
        next = null;
    }
    public MyNode(T value,MyNode<T> next)
    {
        data = value;
        this.next = next;
    }
    public MyNode(MyNode<T> next)
    {
        this.next = next;
    }
}

4.单链表类

/// <summary>
/// 单链表
/// </summary>
public class MyLinkList<T>
{
    private MyNode<T> head;//头结点
    int count = 0;//链表长度
    public MyLinkList()
    {
        head = null;
    }
}

5.单链表的功能实现

(1)获取链表长度

/// <summary>
/// 获取链表长度
/// </summary>
/// <returns></returns>
public int GetLength()
{
    return count;
}

(2)清空列表

/// <summary>
/// 清空列表
/// </summary>
public void Clear()
{
    head = null;
    count = 0;
}

(3)判断链表是否为空

/// <summary>
/// 判断链表是否为空
/// </summary>
/// <returns></returns>
public bool IsEmpty()
{
    return head == null;
}

(4)添加元素

/// <summary>
/// 在链表尾部插入一个结点
/// </summary>
/// <param name="item"></param>
public void Add(T item)
{
    //根据传过来的数据创建一个新的结点
    MyNode<T> newNode = new MyNode<T>(item);
    if (head == null)
    {
        head = newNode;
    }
    else
    {
        //把新结点放到链表的结尾
        MyNode<T> temp = head;
        while (temp.Next != null)
        {
            temp = temp.Next;
        }
        //新结点放到链表尾部
        temp.Next = newNode;
    }
    count++;
}

(5)在指定位置插入元素

/// <summary>
/// 在指定索引位置插入一个结点
/// </summary>
/// <param name="item">数据</param>
/// <param name="index">插入元素的索引位置/param>
public void Insert(T item,int index)
{
    if (index < 0 || index > count - 1) return;
    MyNode<T> newNode = new MyNode<T>(item);
    if (index == 0)//相当于头结点
    {
        newNode.Next = head;
        head = newNode;
    }
    else
    {
        MyNode<T> temp = head;
        //获取到需要插入结点的前一个位置
        for(int i = 1; i < index; i++)
        {
            temp = temp.Next;
        }
        MyNode<T> preNode = temp;
        MyNode<T> curNode = temp.Next;
        preNode.Next = newNode;
        newNode.Next = curNode;
    }
    count++;
}

(6)删除指定位置元素

/// <summary>
/// 删除指定索引的元素
/// </summary>
/// <param name="index">指定的索引</param>
/// <returns>被删除的数据</returns>
public T Delete(int index)
{
    T data = default(T);
    if (index < 0 || index > count - 1) return data;
    if (index == 0)//删除头结点
    {
        data = head.Data;
        head = head.Next;
    }
    else
    {
        MyNode<T> temp = head;
        //获取到需要删除结点的前一个位置
        for (int i = 1; i < index; i++)
        {
            temp = temp.Next;
        }
        MyNode<T> preNode = temp;
        MyNode<T> curNode = temp.Next;
        data = curNode.Data;
        MyNode<T> nextNode = temp.Next.Next;
        preNode.Next = nextNode;
    }
    count--;
    return data;
}

(7)索引器

/// <summary>
/// 索引器
/// </summary>
/// <param name="index"></param>
/// <returns></returns>
public T this[int index]
{
    get
    {
        MyNode<T> temp = head;
        for(int i = 1; i <= index; i++)
        {
            temp = temp.Next;
        }
        return temp.Data;
    }
}

(8)获取指定位置的值

/// <summary>
/// 获取指定索引位置的值
/// </summary>
/// <param name="index">指定的索引</param>
/// <returns></returns>
public T GetEle(int index)
{
    return this[index];
}

(9)获取值所在的位置

/// <summary>
/// 根据数据返回数据所在的索引位置
/// </summary>
/// <param name="value"></param>
/// <returns></returns>
public int Locate(T value)
{
    MyNode<T> temp = head;
    if (temp == null)
    {
        return -1;
    }
    else
    {
        int index = 0;
        while (true)
        {
            if (temp.Data.Equals(value))
            {
                return index;
            }
            else
            {
                if (temp.Next != null)
                {
                    temp = temp.Next;
                    index++;
                }
                else
                {
                    break;
                }
            }
        }
    }
    return -1;
}

(10)打印输出单链表

/// <summary>
/// 格式化打印输出单链表
/// </summary>
public void MToString()
{
    MyNode<T> temp = head;
    Console.Write("单链表输出为: ");
    while (temp.Next != null)
    {
        Console.Write(temp.Data + "->");
        temp = temp.Next;
    }
    Console.WriteLine(temp.Data + "->null");
}

6.测试单链表功能

测试代码:

static void Main(string[] args)
{
    //测试单链表
    MyLinkList<int> myLinkList = new MyLinkList<int>();
    myLinkList.Add(1);
    myLinkList.Add(2);
    myLinkList.Add(3);
    myLinkList.Add(4);
    myLinkList.Add(5);
    myLinkList.MToString();
    Console.WriteLine("单链表是否为空:" + myLinkList.IsEmpty());
    Console.WriteLine("单链表的长度为:" + myLinkList.GetLength());
    Console.WriteLine("获取索引为1的元素:" + myLinkList.GetEle(1));
    Console.WriteLine("通过索引器获取索引为2的元素:" + myLinkList[2]);
    Console.WriteLine("获取元素值为3的索引位置:" + myLinkList.Locate(3));
    myLinkList.Delete(2);
    Console.WriteLine("删除索引为2的结点 ");
    myLinkList.MToString();
    Console.WriteLine("在索引为2的位置插入一个元素100");
    myLinkList.Insert(100, 2);
    myLinkList.MToString();
    Console.WriteLine("清空列表");
    myLinkList.Clear();
    Console.WriteLine("清空列表后的列表长度" + myLinkList.GetLength());
    Console.WriteLine("单链表是否为空:" + myLinkList.IsEmpty());
    Console.ReadKey();
}

输出结果:

7.单链表完整代码

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace 单链表
{
    internal class Program
    {
        static void Main(string[] args)
        {
            //测试单链表
            MyLinkList<int> myLinkList = new MyLinkList<int>();
            myLinkList.Add(1);
            myLinkList.Add(2);
            myLinkList.Add(3);
            myLinkList.Add(4);
            myLinkList.Add(5);
            myLinkList.MToString();
            Console.WriteLine("单链表是否为空:" + myLinkList.IsEmpty());
            Console.WriteLine("单链表的长度为:" + myLinkList.GetLength());
            Console.WriteLine("获取索引为1的元素:" + myLinkList.GetEle(1));
            Console.WriteLine("通过索引器获取索引为2的元素:" + myLinkList[2]);
            Console.WriteLine("获取元素值为3的索引位置:" + myLinkList.Locate(3));
            myLinkList.Delete(2);
            Console.WriteLine("删除索引为2的结点 ");
            myLinkList.MToString();
            Console.WriteLine("在索引为2的位置插入一个元素100");
            myLinkList.Insert(100, 2);
            myLinkList.MToString();
            Console.WriteLine("清空列表");
            myLinkList.Clear();
            Console.WriteLine("清空列表后的列表长度" + myLinkList.GetLength());
            Console.WriteLine("单链表是否为空:" + myLinkList.IsEmpty());
            Console.ReadKey();
        }
    }
    /// <summary>
    /// 单链表的结点
    /// </summary>
    /// <typeparam name="T"></typeparam>
    class MyNode<T>
    {
        T data;//数据域
        MyNode<T> next;//指针域,用来指向下一个元素
        public T Data
        {
            get { return data; }
            set { data = value; }
        }
        //MyNode的各种构造函数
        public MyNode<T> Next
        {
            get { return next; }
            set { next = value; }
        }
        public MyNode()
        {
            data = default(T);
            next = null;
        }
        public MyNode(T value)
        {
            data = value;
            next = null;
        }
        public MyNode(T value,MyNode<T> next)
        {
            data = value;
            this.next = next;
        }
        public MyNode(MyNode<T> next)
        {
            this.next = next;
        }
    }
    /// <summary>
    /// 单链表
    /// </summary>
    public class MyLinkList<T>
    {
        private MyNode<T> head;//头结点
        int count = 0;//链表长度
        public MyLinkList()
        {
            head = null;
        }
        /// <summary>
        /// 获取链表长度
        /// </summary>
        /// <returns></returns>
        public int GetLength()
        {
            return count;
        }
        /// <summary>
        /// 清空列表
        /// </summary>
        public void Clear()
        {
            head = null;
            count = 0;
        }
        /// <summary>
        /// 判断链表是否为空
        /// </summary>
        /// <returns></returns>
        public bool IsEmpty()
        {
            return head == null;
        }
        /// <summary>
        /// 在链表尾部插入一个结点
        /// </summary>
        /// <param name="item"></param>
        public void Add(T item)
        {
            //根据传过来的数据创建一个新的结点
            MyNode<T> newNode = new MyNode<T>(item);
            if (head == null)
            {
                head = newNode;
            }
            else
            {
                //把新结点放到链表的结尾
                MyNode<T> temp = head;
                while (temp.Next != null)
                {
                    temp = temp.Next;
                }
                //新结点放到链表尾部
                temp.Next = newNode;
            }
            count++;
        }
        /// <summary>
        /// 在指定索引位置插入一个结点
        /// </summary>
        /// <param name="item">数据</param>
        /// <param name="index">插入元素的索引位置/param>
        public void Insert(T item, int index)
        {
            if (index < 0 || index > count - 1) return;
            MyNode<T> newNode = new MyNode<T>(item);
            if (index == 0)//相当于头结点
            {
                newNode.Next = head;
                head = newNode;
            }
            else
            {
                MyNode<T> temp = head;
                //获取到需要插入结点的前一个位置
                for(int i = 1; i < index; i++)
                {
                    temp = temp.Next;
                }
                MyNode<T> preNode = temp;
                MyNode<T> curNode = temp.Next;
                preNode.Next = newNode;
                newNode.Next = curNode;
            }
            count++;
        }
        /// <summary>
        /// 删除指定索引的元素
        /// </summary>
        /// <param name="index">指定的索引</param>
        /// <returns>被删除的数据</returns>
        public T Delete(int index)
        {
            T data = default(T);
            if (index < 0 || index > count - 1) return data;
            if (index == 0)//删除头结点
            {
                data = head.Data;
                head = head.Next;
            }
            else
            {
                MyNode<T> temp = head;
                //获取到需要删除结点的前一个位置
                for (int i = 1; i < index; i++)
                {
                    temp = temp.Next;
                }
                MyNode<T> preNode = temp;
                MyNode<T> curNode = temp.Next;
                data = curNode.Data;
                MyNode<T> nextNode = temp.Next.Next;
                preNode.Next = nextNode;
            }
            count--;
            return data;
        }
        /// <summary>
        /// 索引器
        /// </summary>
        /// <param name="index"></param>
        /// <returns></returns>
        public T this[int index]
        {
            get
            {
                MyNode<T> temp = head;
                for(int i = 1; i <= index; i++)
                {
                    temp = temp.Next;
                }
                return temp.Data;
            }
        }
        /// <summary>
        /// 获取指定索引位置的值
        /// </summary>
        /// <param name="index">指定的索引</param>
        /// <returns></returns>
        public T GetEle(int index)
        {
            return this[index];
        }
        /// <summary>
        /// 根据数据返回数据所在的索引位置
        /// </summary>
        /// <param name="value"></param>
        /// <returns></returns>
        public int Locate(T value)
        {
            MyNode<T> temp = head;
            if (temp == null)
            {
                return -1;
            }
            else
            {
                int index = 0;
                while (true)
                {
                    if (temp.Data.Equals(value))
                    {
                        return index;
                    }
                    else
                    {
                        if (temp.Next != null)
                        {
                            temp = temp.Next;
                            index++;
                        }
                        else
                        {
                            break;
                        }
                    }
                }
            }
            return -1;
        }
        /// <summary>
        /// 格式化打印输出单链表
        /// </summary>
        public void MToString()
        {
            MyNode<T> temp = head;
            Console.Write("单链表输出为: ");
            while (temp.Next != null)
            {
                Console.Write(temp.Data + "->");
                temp = temp.Next;
            }
            Console.WriteLine(temp.Data + "->null");
        }
    }
}
  • 2
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值