1

单链表的转置

image.png

image.png

编程实验:单链表的转置

#include <iostream>

using namespace std;

struct Node
{
    int value;
    Node *next;
};

Node *create_list(int v, int len)
{
    Node *ret = nullptr;
    Node *slider = nullptr;

    for (int i=0; i<len; ++i)
    {
        Node *n = new Node();

        n->value = v++;
        n->next = nullptr;

        if (slider == nullptr)
        {
            slider = n;
            ret = n;
        }
        else
        {
            slider->next = n;
            slider = n;
        }
    }

    return ret;
};

void destroy_list(Node *list)
{
    while (list)
    {
        Node *del = list;

        list = list->next;

        delete del;
    }
}

void print_list(Node *list)
{
    while (list)
    {
        cout << list->value << "->";
        list = list->next;
    }

    cout << "NULL" << endl;
}

Node *reverse(Node *list)
{
    if ((list == nullptr) || (list->next == nullptr))
    {
        return list;
    }
    else
    {
        Node *guard = list->next;
        Node *ret = reverse(list->next);
        guard->next = list;
        list->next = nullptr;

        return ret;
    }
}

int main()
{
    Node *list = create_list(1, 5);

    print_list(list);

    list = reverse(list);

    print_list(list);

    destroy_list(list);

    return 0;
}

输出:

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

单向排序链表的合并

image.png

image.png

编程实验:单向排序链表的合并

#include <iostream>

using namespace std;

struct Node
{
    int value;
    Node *next;
};

Node *create_list(int v, int len)
{
    Node *ret = nullptr;
    Node *slider = nullptr;

    for (int i=0; i<len; ++i)
    {
        Node *n = new Node();

        n->value = v++;
        n->next = nullptr;

        if (slider == nullptr)
        {
            slider = n;
            ret = n;
        }
        else
        {
            slider->next = n;
            slider = n;
        }
    }

    return ret;
};

void destroy_list(Node *list)
{
    while (list)
    {
        Node *del = list;

        list = list->next;

        delete del;
    }
}

void print_list(Node *list)
{
    while (list)
    {
        cout << list->value << "->";
        list = list->next;
    }

    cout << "NULL" << endl;
}

Node *merge(Node *list1, Node *list2)
{
    if (list1 == nullptr)
    {
        return list2;
    }
    else if (list2 == nullptr)
    {
        return list1;
    }
    else
    {
        if (list1->value < list2->value)
        {
            return (list1->next = merge(list1->next, list2), list1);
        }
        else
        {
            return (list2->next = merge(list1, list2->next), list2);
        }
    }
}

int main()
{
    Node *list1 = create_list(1, 5);
    Node *list2 = create_list(2, 6);

    print_list(list1);
    print_list(list2);

    Node *list = merge(list1, list2);

    print_list(list);

    destroy_list(list);

    return 0;
}

输出:

1->2->3->4->5->NULL
2->3->4->5->6->7->NULL
1->2->2->3->3->4->4->5->5->6->7->NULL

汉诺塔问题

将木块借助 B 柱由 A 柱移动到 C 柱
每次只能移动一个木块
只能出现小木块在大木块之上

image.png

汉诺塔问题分解

  • 将 n-1 个木块借助 C 柱由 A 柱移动到 B 柱
  • 将最底层的唯一木块直接一定到 C 柱
  • 将 n-1 个木块借助 A 柱移动到 C 柱

编程实验:汉诺塔问题求解

#include <iostream>

using namespace std;

void hanoiTower(int n, char a, char b, char c)
{
    if (n == 1)
    {
        cout << a << "->" << c << endl;
    }
    else
    {
        hanoiTower(n-1, a, c, b);
        hanoiTower(1, a, b, c);
        hanoiTower(n-1, b, a, c);
    }
}

int main()
{
    hanoiTower(3, 'a', 'b', 'c');

    return 0;
}

输出:

a->c
a->b
c->b
a->c
b->a
b->c
a->c

全排列问题

image.png

编程实验:全排列的递归解法

#include <iostream>
#include <cstring>

using namespace std;

void permutation(char *s, char *e)
{
    if (*s == '\0')
    {
        cout << e << endl;
    }
    else
    {
        size_t len = strlen(s);
        for (size_t i=0; i<len; ++i)
        {
            if ((i == 0) || (s[0] != s[i]))
            {
                swap(s[0], s[i]);
                permutation(s + 1, e);
                swap(s[0], s[i]);
            }
        }
    }
}

int main()
{
    char s1[] = "abc";
    permutation(s1, s1);

    cout << "----------" << endl;
    char s2[] = "aac";
    permutation(s2, s2);

    return 0;
}

输出:

abc
acb
bac
bca
cba
cab
----------
aac
aca
caa

以上内容整理于狄泰软件学院系列课程,请大家保护原创!


TianSong
737 声望139 粉丝

阿里山神木的种子在3000年前已经埋下,今天不过是看到当年注定的结果,为了未来的自己,今天就埋下一颗好种子吧