白骑士的C语言教学高级篇 3.2 高级数据结构

系列目录

上一篇:白骑士的C语言教学高级篇 3.1 高级指针技术

        在计算机科学中,数据结构是组织和存储数据的方式,不同的数据结构适用于不同的问题和算法。本节将介绍链表、栈与队列以及树与图,这些高级数据结构在实际编程中非常常用,并且是许多复杂算法的基础。

链表

        链表是一种线性数据结构,其中的元素存储在节点中,每个节点包含数据和一个指向下一个节点的指针。链表的优点是插入和删除操作非常高效,但缺点是访问元素的时间复杂度较高,因为需要从头节点开始逐个遍历。

单向链表

        只有一个方向的指针,指向下一个节点,例如:

#include <stdio.h>
#include <stdlib.h>


typedef struct Node {
    int data;

    struct Node *next;
} Node;


void append(Node **head, int data) {
    Node *new_node = (Node *)malloc(sizeof(Node));

    new_node->data = data;
    new_node->next = NULL;

    if (*head == NULL) {
        *head = new_node;
    } 

    else {
        Node *temp = *head;

        while (temp->next != NULL) {
            temp = temp->next;
        }

        temp->next = new_node;
    }
}


void printList(Node *head) {
    while (head != NULL) {
        printf("%d -> ", head->data);

        head = head->next;
    }

    printf("NULL\n");
}


int main() {
    Node *head = NULL;

    append(&head, 1);
    append(&head, 2);
    append(&head, 3);

    printList(head);

    return 0;
}

双向链表

        具有两个方向的指针,分别指向前一个节点和后一个节点,例如:

#include <stdio.h>
#include <stdlib.h>


typedef struct Node {
    int data;

    struct Node *prev;
    struct Node *next;
} Node;


void append(Node **head, int data) {
    Node *new_node = (Node *)malloc(sizeof(Node));
    new_node->data = data;
    new_node->next = NULL;

    if (*head == NULL) {
        new_node->prev = NULL;

        *head = new_node;
    } 

    else {
        Node *temp = *head;

        while (temp->next != NULL) {
            temp = temp->next;
        }

        temp->next = new_node;

        new_node->prev = temp;
    }
}


void printList(Node *head) {
    while (head != NULL) {
        printf("%d -> ", head->data);

        head = head->next;
    }

    printf("NULL\n");
}


int main() {
    Node *head = NULL;

    append(&head, 1);
    append(&head, 2);
    append(&head, 3);

    printList(head);

    return 0;
}

栈与队列

        栈(Stack)是一种后进先出(LIFO,Last In First Out)的数据结构,栈的操作主要有两个:‘push‘(入栈)和 ‘pop‘(出栈)。例如:

#include <stdio.h>
#include <stdlib.h>


#define MAX 100


typedef struct Stack {
    int data[MAX];
    int top;
} Stack;


void push(Stack *stack, int value) {
    if (stack->top < MAX - 1) {
        stack->data[++stack->top] = value;
    } 

    else {
        printf("Stack overflow\n");
    }
}


int pop(Stack *stack) {
    if (stack->top >= 0) {
        return stack->data[stack->top--];
    } 

    else {
        printf("Stack underflow\n");

        return -1;
    }
}


int main() {
    Stack stack;
    stack.top = -1;

    push(&stack, 1);
    push(&stack, 2);
    push(&stack, 3);

    printf("Popped: %d\n", pop(&stack));
    printf("Popped: %d\n", pop(&stack));

    return 0;
}

队列

        队列(Queue)是一种先进先出(FIFO,First In First Out)的数据结构,队列的操作主要有两个:‘enqueue‘(入队)和 ‘dequeue‘(出队)。例如:

#include <stdio.h>
#include <stdlib.h>


#define MAX 100


typedef struct Queue {
    int data[MAX];
    int front;
    int rear;
} Queue;


void enqueue(Queue *queue, int value) {
    if (queue->rear < MAX - 1) {
        queue->data[++queue->rear] = value;

        if (queue->front == -1) {
            queue->front = 0;
        }
    } 

    else {
        printf("Queue overflow\n");
    }
}


int dequeue(Queue *queue) {
    if (queue->front > queue->rear || queue->front == -1) {
        printf("Queue underflow\n");

        return -1;
    } 

    else {
        return queue->data[queue->front++];
    }
}


int main() {
    Queue queue;
    queue.front = -1;
    queue.rear = -1;

    enqueue(&queue, 1);
    enqueue(&queue, 2);
    enqueue(&queue, 3);

    printf("Dequeued: %d\n", dequeue(&queue));
    printf("Dequeued: %d\n", dequeue(&queue));

    return 0;
}

树与图

        树(Tree)是一种层次数据结构,树中的每个节点包含一个数据元素和指向子节点的指针。树的典型应用包括二叉树、二叉搜索树(BST)等。

        二叉树是一种特殊的树结构,每个节点最多有两个子节点,例如:

#include <stdio.h>
#include <stdlib.h>


typedef struct Node {
    int data;

    struct Node *left;
    struct Node *right;
} Node;


Node* createNode(int data) {
    Node *newNode = (Node *)malloc(sizeof(Node));
    newNode->data = data;
    newNode->left = NULL;
    newNode->right = NULL;

    return newNode;
}


void inorderTraversal(Node *root) {
    if (root != NULL) {
        inorderTraversal(root->left);

        printf("%d -> ", root->data);

        inorderTraversal(root->right);
    }
}


int main() {
    Node *root = createNode(1);
    root->left = createNode(2);
    root->right = createNode(3);
    root->left->left = createNode(4);
    root->left->right = createNode(5);

    printf("Inorder Traversal: ");

    inorderTraversal(root);

    printf("NULL\n");

    return 0;
}

        图(Graph)是一种更复杂的数据结构,由节点(顶点)和边组成。图可以是有向图或无向图,应用广泛,如社交网络、交通网络等。

        邻接矩阵表示法是图的一种表示方法,例如:

#include <stdio.h>


#define MAX 5


void addEdge(int graph[MAX][MAX], int u, int v) {
    graph[u][v] = 1;
    graph[v][u] = 1;  // 如果是无向图
}


void printGraph(int graph[MAX][MAX]) {
    for (int i = 0; i < MAX; i++) {
        for (int j = 0; j < MAX; j++) {
            printf("%d ", graph[i][j]);
        }

        printf("\n");
    }
}


int main() {
    int graph[MAX][MAX] = {0};

    addEdge(graph, 0, 1);
    addEdge(graph, 0, 4);
    addEdge(graph, 1, 2);
    addEdge(graph, 1, 3);
    addEdge(graph, 1, 4);
    addEdge(graph, 2, 3);
    addEdge(graph, 3, 4);

    printGraph(graph);

    return 0;
}

总结

        高级数据结构在C语言编程中具有重要地位,掌握这些数据结构可以解决复杂的问题,提高程序的效率和灵活性。通过链表、栈与队列以及树与图的学习,将具备处理多种实际应用场景的能力。这些数据结构不仅在算法设计中广泛应用,而且是计算机科学领域的基础知识。

下一篇:白骑士的C语言教学高级篇 3.3 并发与多线程​​​​​​​

  • 9
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

白骑士所长

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值