📜  如何删除节点 c++ (1)

📅  最后修改于: 2023-12-03 14:52:09.454000             🧑  作者: Mango

如何删除节点

在C++中,删除一个节点指的是从链表或二叉树中移除特定节点的操作。下面我们将介绍如何删除一个节点,并提供相关的代码示例。

删除单链表中的节点

要删除单链表中的节点,需要考虑以下几个情况:

  1. 删除头节点
  2. 删除中间节点
  3. 删除尾节点

下面是一个示例单链表的结构定义:

struct ListNode {
    int val;
    ListNode* next;
};
删除头节点

删除头节点时,我们需要将头节点的下一个节点作为新的头节点。可以使用以下代码来删除头节点:

void deleteHead(ListNode** head) {
    if (*head == NULL) {
        // 链表为空,无需删除
        return;
    }
    ListNode* temp = *head;
    *head = (*head)->next;
    delete temp;
}
删除中间节点

删除中间节点时,我们需要找到目标节点的前一个节点,将其指向目标节点的下一个节点。可以使用以下代码来删除中间节点:

void deleteNode(ListNode** head, int target) {
    ListNode* current = *head;
    ListNode* previous = NULL;
    
    while (current != NULL) {
        if (current->val == target) {
            if (previous == NULL) {
                // 目标节点为头节点
                *head = current->next;
            } else {
                previous->next = current->next;
            }
            
            delete current;
            break;
        }
        
        previous = current;
        current = current->next;
    }
}
删除尾节点

删除尾节点时,我们需要找到尾节点的前一个节点,将其指向NULL,并删除尾节点。可以使用以下代码来删除尾节点:

void deleteTail(ListNode** head) {
    if (*head == NULL) {
        // 链表为空,无需删除
        return;
    }
    
    ListNode* current = *head;
    ListNode* previous = NULL;
    
    while (current->next != NULL) {
        previous = current;
        current = current->next;
    }
    
    if (previous == NULL) {
        // 链表只有一个节点
        *head = NULL;
    } else {
        previous->next = NULL;
    }
    
    delete current;
}
删除二叉树中的节点

删除二叉树中的节点有以下几种情况:

  1. 删除叶子节点
  2. 删除拥有一个子节点的节点
  3. 删除拥有两个子节点的节点

下面是一个示例二叉树的结构定义:

struct TreeNode {
    int val;
    TreeNode* left;
    TreeNode* right;
};
删除叶子节点

删除叶子节点时,只需将其父节点指向它的指针设置为NULL,并删除该叶子节点。可以使用以下代码来删除叶子节点:

void deleteLeaf(TreeNode** parent, TreeNode* leaf) {
    if (*parent == NULL || leaf == NULL) {
        // 无需删除或指针为空
        return;
    }
    
    if ((*parent)->left == leaf) {
        (*parent)->left = NULL;
    } else if ((*parent)->right == leaf) {
        (*parent)->right = NULL;
    }
    
    delete leaf;
}
删除拥有一个子节点的节点

删除拥有一个子节点的节点时,只需将其父节点指向它的指针指向它的子节点,并删除该节点。可以使用以下代码来删除拥有一个子节点的节点:

void deleteNodeWithOneChild(TreeNode** parent, TreeNode* node) {
    if (*parent == NULL || node == NULL) {
        // 无需删除或指针为空
        return;
    }
    
    if ((*parent)->left == node) {
        if (node->left != NULL) {
            (*parent)->left = node->left;
        } else {
            (*parent)->left = node->right;
        }
    } else if ((*parent)->right == node) {
        if (node->left != NULL) {
            (*parent)->right = node->left;
        } else {
            (*parent)->right = node->right;
        }
    }
    
    delete node;
}
删除拥有两个子节点的节点

删除拥有两个子节点的节点时,需要找到其后继节点(右子树中值最小的节点),将其值赋给该节点,然后删除后继节点。可以使用以下代码来删除拥有两个子节点的节点:

void deleteNodeWithTwoChildren(TreeNode** parent, TreeNode* node) {
    if (*parent == NULL || node == NULL) {
        // 无需删除或指针为空
        return;
    }
    
    TreeNode* successor = node->right;
    
    while (successor->left != NULL) {
        successor = successor->left;
    }
    
    node->val = successor->val;
    
    if (successor->right != NULL) {
        deleteNodeWithOneChild(&successor, successor->right);
    } else {
        deleteLeaf(&successor, successor);
    }
}

以上就是在C++中删除节点的方法和示例代码。无论是删除单链表中的节点还是删除二叉树中的节点,我们都需要处理好指针的指向,并释放被删除节点的内存。根据具体的需求,选择适合的删除方式可以提高代码的效率和可读性。