C++程序 计算已排序旋转链表中的旋转数

C++程序 计算已排序旋转链表中的旋转数

在面试中,经常会遇到计算旋转链表的问题。旋转链表是一种具有循环移位的链表,即将链表的最后一个元素移到第一个元素之前。但是,并不是所有旋转链表都是由顺序排列的,因此需要计算已排序旋转链表中旋转的元素。在本文中,我们将介绍如何通过使用C++编写程序来计算已排序旋转链表中的旋转数。

什么是旋转链表?

首先,让我们来了解一下什么是旋转链表。旋转链表是一个环形链表,最后一个元素后面连接到第一个元素之前。例如,以下是一个旋转链表的示例:

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

需要注意的是,所有的旋转链表都是有序的。

旋转数是什么?

旋转链表由顺序链表旋转而成。链表中被旋转的元素的数量被称为旋转数。例如,以下是一个旋转数为2的旋转链表的示例:

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

旋转数是非常重要的,因为它可以告诉我们进行旋转的次数。通过计算旋转数,我们可以确定在旋转操作中,需要将链表移位几次才能完成所有操作。

如何计算已排序旋转链表中的旋转数?

C++中,计算已排序旋转链表中的旋转数可以通过以下三个步骤完成:

第一步:查找中间节点

首先,需要找到链表的中间节点。为了完成这个步骤,可以使用快慢指针的方法。快指针每次向前移动两个位置,而慢指针每次移动一个位置。快指针到达链表末尾时,慢指针应该正好在链表的中间。以下是示例代码:

ListNode* findMiddle(ListNode* head) {
    ListNode* slow = head;
    ListNode* fast = head;

    while (fast != nullptr && fast->next != nullptr) {
        slow = slow->next;
        fast = fast->next->next;
    }

    return slow;
}

第二步:查找中间节点后的下一个节点

一旦找到链表的中间节点,接下来需要找到中间节点后的下一个节点。此节点是旋转位置。以下是示例代码:

ListNode* findRotation(ListNode* head) {
    ListNode* middle = findMiddle(head);
    ListNode* rotation = middle->next;
    middle->next = nullptr;
    return rotation;
}

第三步:计算旋转数

最后,需要计算中间节点的下一个节点(旋转位置)的位置,以确定旋转数。以下是示例代码:

int findRotateCount(ListNode* head) {
    ListNode* rotation = findRotation(head);
    ListNode* current = rotation;
    int count = 1;

    while (current->next != nullptr) {
        current = current->next;
        count++;
    }

    return count;
}

完整代码

以下是计算已排序旋转链表中的旋转数的完整代码:

#include <iostream>

using namespace std;

struct ListNode {
    int val;
    ListNode* next;
    ListNode(int x) : val(x), next(nullptr) {}
};

ListNode* findMiddle(ListNode* head) {
    ListNode* slow = head;
    ListNode* fast = head;

    while (fast != nullptr && fast->next != nullptr) {
        slow = slow->next;
        fast =fast->next->next;
    }

    return slow;
}

ListNode* findRotation(ListNode* head) {
    ListNode* middle = findMiddle(head);
    ListNode* rotation = middle->next;
    middle->next = nullptr;
    return rotation;
}

int findRotateCount(ListNode* head) {
    ListNode* rotation = findRotation(head);
    ListNode* current = rotation;
    int count = 1;

    while (current->next != nullptr) {
        current = current->next;
        count++;
    }

    return count;
}

int main() {
    ListNode* head = new ListNode(1);
    ListNode* node1 = new ListNode(2);
    ListNode* node2 = new ListNode(3);
    ListNode* node3 = new ListNode(4);
    ListNode* node4 = new ListNode(5);

    head->next = node1;
    node1->next = node2;
    node2->next = node3;
    node3->next = node4;
    node4->next = head;

    int rotateCount = findRotateCount(head);  // 0

    ListNode* newHead = new ListNode(3);
    ListNode* newNode1 = new ListNode(4);
    ListNode* newNode2 = new ListNode(5);
    ListNode* newNode3 = new ListNode(1);
    ListNode* newNode4 = new ListNode(2);

    newHead->next = newNode1;
    newNode1->next = newNode2;
    newNode2->next = newNode3;
    newNode3->next = newNode4;
    newNode4->next = newHead;

    rotateCount = findRotateCount(newHead);  // 2

    cout << "Rotate count is: " << rotateCount << endl;

    return 0;
}

在上面的代码中,我们创建了一个包含5个元素的链表,并将其连接到环的起点。然后,我们计算旋转数,并打印结果为0。接下来,我们创建了一个具有两个元素旋转的链表,并再次计算旋转数。此时,结果应该是2。最后,我们打印旋转数。

结论

通过使用C++,可以轻松计算已排序旋转链表中的旋转数。通过遵循上述三个步骤,可以在面试中便捷地解决旋转链表的相关问题。

Camera课程

Python教程

Java教程

Web教程

数据库教程

图形图像教程

办公软件教程

Linux教程

计算机教程

大数据教程

开发工具教程

C++ 示例