【leetcode】链表的基本操作

题目一:

Reverse a singly linked list.
1->2->3->NULL
NULL-<1-<2-<3

解法:
/**
 * Definition for singly-linked list.
 * struct ListNode {
 *     int val;
 *     ListNode *next;
 *     ListNode(int x) : val(x), next(NULL) {}
 * };
 */
class Solution {
public:
    ListNode* reverseList(ListNode* head) {

        ListNode* pre=NULL;
        ListNode* cur=head;

        while(cur!=NULL)
        {
            ListNode* next=cur->next;

            cur->next=pre;

            pre=cur;
            cur=next;
        }

        return pre;

    }
};

题目二:Reverse Linked List II

Reverse Linked List II

Reverse a linked list from position m to n. Do it in-place and in
one-pass.

For example: Given 1->2->3->4->5->NULL, m = 2 and n = 4,

return 1->4->3->2->5->NULL.

Note: Given m, n satisfy the following condition: 1 ≤ m ≤ n ≤ length
of list.

解法:
ListNode *reverseBetween(ListNode *head, int m, int n)
{
    if (m == n||head==NULL)
        return head;
    n -= m;
    //定义一个虚拟头结点,这样方便找到上一个结点
    ListNode prehead(0);
    prehead._next = head;
    ListNode* pre = &prehead;
    //找到起始结点的上一个结点
    while (--m)pre = pre->_next;
    ListNode *pCur = pre->_next;

    while (n--)
    {
        ListNode *pNext= pCur->_next;

        pCur->_next = pNext->_next;
        pNext->_next = pre->_next;
        pre->_next = pNext;
    }
    return prehead._next;
}

题目三: Remove Duplicates from Sorted List

Remove Duplicates from Sorted List

Given a sorted linked list, delete all duplicates such that each
element appear only once.

For example, Given 1->1->2, return 1->2. Given 1->1->2->3->3, return
1->2->3.
译文:给定一个排序的链接列表,删除所有重复项,使每个元素只显示一次。

   ListNode* deleteDuplicates(ListNode* head) 
{
    if (head == NULL||head->next==NULL)
        return head;
    ListNode* pre= head;
    ListNode* cur = pre->next;
    while (NULL!=cur)
    {
        //判断是否与上一个元素重复,如果重复是,进行穿针引线
        if (pre->val == cur->val)
        {
            ListNode* del = cur;
            cur= cur->next;
            pre->next = cur;
            delete del;
            del = NULL;
        }
        else//继续下一次探测
        {
            pre = cur;
            cur = cur->next;
        }
    }
    return head;
}

题目四:Partition List

Partition List
题目描述:

Given a linked list and a value x, partition it such that all nodes less than x come before nodes greater than or equal to x.

You should preserve the original relative order of the nodes in each of the two partitions.

For example,
Given 1->4->3->2->5->2 and x = 3,
return 1->2->2->4->3->5.

译文:给定一个链表和一个值x,对其进行分区,使得小于x的所有节点都在大于或等于x的节点之前。

您应该保留两个分区中每个分区中节点的原始相对顺序。

ListNode *partition(ListNode *head, int x)
{
    ListNode node1(0), node2(0);//因为要分段定义了两虚拟头结点
    ListNode* p1 = &node1, *p2 = &node2;
    while (head)
    {
        if (head->val < x)
        {
            p1 = p1->next = head;
        }
        else
        {
            p2 = p2->next = head;
        }
        head = head->next;
    }
    p2->next=NULL;//head==NULL时,并没有把NULL赋给p2->next
    p1->next = node2.next;
    return node1.next;
}

题目五:Add Two Numbers

dd Two Numbers
题目描述:

You are given two non-empty linked lists representing two non-negative
integers. The digits are stored in reverse order and each of their
nodes contain a single digit. Add the two numbers and return it as a
linked list.

You may assume the two numbers do not contain any leading zero, except
the number 0 itself.

Input: (2 -> 4 -> 3) + (5 -> 6 -> 4) Output: 7 -> 0 -> 8

译文:给定两个非空的链表,表示两个非负整数。数字以相反的顺序存储,每个节点包含一个数字。求和两个数字并将其作为链表返回。

您可以假设两个数字不包含任何前导零,除了数字0本身。

ListNode* addTwoNumbers(ListNode* l1, ListNode* l2) {
        ListNode preHead(0), *p = &preHead;
    int extra = 0;
    while (l1 || l2 || extra) {
        int sum = (l1 ? l1->val : 0) + (l2 ? l2->val : 0) + extra;
        extra = sum / 10;
        p->next = new ListNode(sum % 10);
        p = p->next;
        l1 = l1 ? l1->next : l1;
        l2 = l2 ? l2->next : l2;
    }
    return preHead.next;
    }

题目六:Remove Linked List Elements

 ListNode* removeElements(ListNode* head, int val) {

      ListNode** cur=&head;

      while(*cur)
      {
          if((*cur)->val==val)
          {
              *cur=(*cur)->next;//修改内容
          }
          else
          {
              cur=&(*cur)->next;//修改临时变量
          }

      }
      return head;
    }

题目七:Remove Duplicates from Sorted List II

Remove Duplicates from Sorted List II

Given a sorted linked list, delete all nodes that have duplicate
numbers, leaving only distinct numbers from the original list.

Given
1->1->1->2->3, return 2->3.

解法一:

 ListNode *deleteDuplicates(ListNode *head)
{
    if (head == NULL || head->next == NULL)
    {
        return head;
    }
    ListNode** runner = &head;

    while (*runner)
    {
        if ((*runner)->next && (*runner)->next->val == (*runner)->val)
        {
            ListNode* temp = *runner;
            while (temp && (*runner)->val == temp->val)
            {
                temp = temp->next;
            }
            *runner = temp;
        }
        else
        {
            runner = &(*runner)->next;
        }
    }
    return head;
}

解法二:

ListNode* deleteDuplicates(ListNode* head) {
        if (!head) return 0;
        if (!head->next) return head;

        int val = head->val;
        ListNode* p = head->next;

        if (p->val != val) {
            head->next = deleteDuplicates(p);
            return head;
        } else {
            while (p && p->val == val) p = p->next;
            return deleteDuplicates(p);
        }
    }

题目八:Merge Two Sorted Lists

Merge Two Sorted Lists
描述:

Merge two sorted linked lists and return it as a new list. The new list should be made by splicing together the nodes of the first two lists.

解法一:

ListNode* mergeTwoLists(ListNode* l1, ListNode* l2) {
if (l1 == NULL)
{
return l2;
}
if (l2 == NULL)
{
return l1;
}
ListNode* ret = NULL;
if (l1->val > l2->val)
{
ret = l2;
l2 = l2->next;
}
else
{
ret = l1;
l1 = l1->next;
}
ListNode * cur = ret;
while (l1&&l2)
{
if (l1->val > l2->val)
{
cur->next = l2;
l2 = l2->next;
}
else
{
cur->next = l1;
l1 = l1->next;
}
cur = cur->next;
}
if (l1 == NULL)
{
cur->next = l2;
}
else
{
cur->next = l1;
}
return ret;
}



解法二:使用虚拟头结点,简化问题。

ListNode* mergeTwoLists(ListNode* l1, ListNode* l2)
{
//定义一个虚拟头结点
ListNode dummy(INT_MIN);
ListNode* tail = &dummy;

while (l1&&l2)
{
    if (l1->val < l2->val)
    {
        tail->next = l1;
        l1 = l1->next;
    }
    else
    {
        tail->next = l2;
        l2 = l2->next;
    }
    tail = tail->next;
}
tail->next = l1 ? l1 : l2;
return dummy.next;

}

问题九:Swap Nodes in Pairs

Swap Nodes in Pairs
描述:

Given a linked list, swap every two adjacent nodes and return its
head.

For example, Given 1->2->3->4, you should return the list as
2->1->4->3.

Your algorithm should use only constant space. You may not modify the
values in the list, only nodes itself can be changed.

译文:

给定一个链表,交换每两个相邻的节点并返回其头。

ListNode* swapPairs(ListNode* head)
{
    ListNode **pp = &head, *a, *b;
    while ((a = *pp) && (b = a->next))
    {
        a->next = b->next;
        b->next = a;

        *pp = b;
        pp = &(a->next);
    }
    return head;
}

问题十: Reverse Nodes in k-Group

Reverse Nodes in k-Group
描述:

Given a linked list, reverse the nodes of a linked list k at a time and return its modified list.

k is a positive integer and is less than or equal to the length of the
linked list. If the number of nodes is not a multiple of k then
left-out nodes in the end should remain as it is.

You may not alter the values in the nodes, only nodes itself may be
changed.

Only constant memory is allowed.

For example, Given this linked list: 1->2->3->4->5
For k = 2, you should return: 2->1->4->3->5
For k = 3, you should return: 3->2->1->4->5

ListNode* reverseKGroup(ListNode* head, int k)
{
    if (head == NULL || k == 1)return head;

    int num = 0;
    ListNode prehead(-1);
    ListNode *preheader = &prehead;

    preheader->next = head;

    ListNode *cur = preheader, *nex, *pre = preheader;

    while (cur = cur->next)num++;

    while (num >= k)
    {
        cur = pre->next;
        nex = cur->next;

        for (int i = 1; i < k; ++i)
        {
            cur->next = nex->next;
            nex->next = pre->next;

            pre->next = nex;
            nex = cur->next;
        }
        pre = cur;
        num -= k;

    }
    return preheader->next;
}
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Rust 是一种现代的编程语言,特别适合处理内存安全和线程安全的代码。在 LeetCode 中,链表是经常出现的题目练习类型,Rust 语言也是一种非常适合处理链表的语言。接下来,本文将从 Rust 语言的特点、链表的定义和操作,以及 Rust 在 LeetCode链表题目的练习等几个方面进行介绍和讲解。 Rust 语言的特点: Rust 是一种现代化的高性能、系统级、功能强大的编程语言,旨在提高软件的可靠性和安全性。Rust 语言具有如下几个特点: 1. 内存安全性:Rust 语言支持内存安全性和原语级的并发,可以有效地预防内存泄漏,空悬指针以及数据竞争等问题,保证程序的稳定性和可靠性。 2. 高性能:Rust 语言采用了“零成本抽象化”的设计思想,具有 C/C++ 等传统高性能语言的速度和效率。 3. 静态类型检查:Rust 语言支持静态类型检查,可以在编译时检查类型错误,避免一些运行时错误。 链表的定义和操作: 链表是一种数据结构,由一个个节点组成,每个节点保存着数据,并指向下一个节点。链表的定义和操作如下: 1. 定义:链表是由节点组成的数据结构,每个节点包含一个数据元素和一个指向下一个节点的指针。 2. 操作:链表的常用操作包括插入、删除、查找等,其中,插入操作主要包括在链表首尾插入节点和在指定位置插入节点等,删除操作主要包括删除链表首尾节点和删除指定位置节点等,查找操作主要包括根据数据元素查找节点和根据指针查找节点等。 Rust 在 LeetCode链表题目的练习: 在 LeetCode 中,链表是常见的题目类型,而 Rust 语言也是一个非常适合练习链表题目的语言。在 Rust 中,我们可以定义结构体表示链表的节点,使用指针表示节点的指向关系,然后实现各种操作函数来处理链表操作。 例如,针对 LeetCode 中的链表题目,我们可以用 Rust 语言来编写解法,例如,反转链表,合并两个有序链表,删除链表中的重复元素等等,这样可以更好地熟悉 Rust 语言的使用和链表的操作,提高算法和编程能力。 总之,在 Rust 中处理链表是非常方便和高效的,而 LeetCode 中的练习也是一个非常好的机会,让我们更好地掌握 Rust 语言和链表数据结构的知识。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值