MST

星途 面试题库

面试题:C语言malloc分配结构体数组内存的复杂场景与优化

有一个结构体struct node { int data; struct node *next; }; 要求使用malloc构建一个链表,链表节点数量由用户输入决定。在构建链表过程中,要对每次malloc分配内存进行错误处理。并且,当链表构建完成后,实现一个函数对链表进行逆序操作,同时分析在这个过程中内存分配与释放可能存在的性能问题,并提出优化方案。
18.4万 热度难度
编程语言C

知识考点

AI 面试

面试题答案

一键面试
#include <stdio.h>
#include <stdlib.h>

// 定义链表节点结构体
struct node {
    int data;
    struct node *next;
};

// 创建新节点
struct node* createNode(int value) {
    struct node* newNode = (struct node*)malloc(sizeof(struct node));
    if (newNode == NULL) {
        fprintf(stderr, "内存分配失败\n");
        exit(EXIT_FAILURE);
    }
    newNode->data = value;
    newNode->next = NULL;
    return newNode;
}

// 构建链表
struct node* buildList(int n) {
    struct node *head = NULL, *tail = NULL;
    for (int i = 0; i < n; i++) {
        int value;
        printf("请输入第 %d 个节点的值: ", i + 1);
        scanf("%d", &value);
        struct node* newNode = createNode(value);
        if (head == NULL) {
            head = newNode;
            tail = newNode;
        } else {
            tail->next = newNode;
            tail = newNode;
        }
    }
    return head;
}

// 逆序链表
struct node* reverseList(struct node* head) {
    struct node *prev = NULL, *current = head, *next = NULL;
    while (current != NULL) {
        next = current->next;
        current->next = prev;
        prev = current;
        current = next;
    }
    return prev;
}

// 打印链表
void printList(struct node* head) {
    struct node* current = head;
    while (current != NULL) {
        printf("%d -> ", current->data);
        current = current->next;
    }
    printf("NULL\n");
}

// 释放链表内存
void freeList(struct node* head) {
    struct node* current = head;
    struct node* next;
    while (current != NULL) {
        next = current->next;
        free(current);
        current = next;
    }
}

int main() {
    int n;
    printf("请输入链表节点的数量: ");
    scanf("%d", &n);

    struct node* head = buildList(n);
    printf("原始链表: ");
    printList(head);

    head = reverseList(head);
    printf("逆序后的链表: ");
    printList(head);

    freeList(head);
    return 0;
}

内存分配与释放性能问题及优化方案

  1. 性能问题

    • 频繁内存分配:在构建链表过程中,每次使用 malloc 分配内存可能会带来一定的开销,特别是当链表节点数量较多时,这种频繁的系统调用可能会影响性能。
    • 内存碎片:频繁的内存分配和释放可能导致内存碎片,使得后续的内存分配请求更难满足,降低内存利用率。
  2. 优化方案

    • 内存池:可以使用内存池技术,预先分配一块较大的内存空间,然后从这个内存池中分配小块内存给链表节点使用。这样可以减少 malloc 的调用次数,提高性能。
    • 批量分配:一次性分配多个节点所需的内存,然后再逐个构建链表节点,这样可以减少内存分配的次数。例如,每次分配10个节点的内存,然后依次使用这些内存构建节点,当用完这10个节点的内存后,再分配下一批。
    • 优化释放策略:在释放链表内存时,可以考虑延迟释放或者批量释放,以减少内存碎片的产生。例如,可以将链表节点的内存先标记为可重用,而不是立即释放,当需要新的节点时,优先从这些可重用的节点中获取。