代码随想录算法训练营第四天 | 24. 两两交换链表中的节点、19.删除链表的倒数第N个节点、面试题 02.07. 链表相交、142.环形链表II

代码随想录算法训练营第四天 | 24. 两两交换链表中的节点、19.删除链表的倒数第N个节点、面试题 02.07. 链表相交、142.环形链表II

文章目录

  • 代码随想录算法训练营第四天 | 24. 两两交换链表中的节点、19.删除链表的倒数第N个节点、面试题 02.07. 链表相交、142.环形链表II
    • 1 LeetCode 24. 两两交换链表中的节点
    • 2 LeetCode 19.删除链表的倒数第N个节点
      • 2.1 2009年408算法题
      • 2.2 LeetCode19题
    • 3 LeetCode 面试题 02.07. 链表相交
      • 3.1 2012年408算法题
      • 3.2 LeetCode 面试题 02.07题
    • 4 LeetCode 142.环形链表II
      • 4.1 快慢指针
      • 4.2 哈希表

1 LeetCode 24. 两两交换链表中的节点

题目链接:https://leetcode.cn/problems/swap-nodes-in-pairs/description/

给你一个链表,两两交换其中相邻的节点,并返回交换后链表的头节点。你必须在不修改节点内部的值的情况下完成本题(即,只能进行节点交换)。

示例 1:

在这里插入图片描述

输入:head = [1,2,3,4]
输出:[2,1,4,3]

示例 2:

输入:head = []
输出:[]

示例 3:

输入:head = [1]
输出:[1]

提示:

  • 链表中节点的数目在范围 [0, 100]
  • 0 <= Node.val <= 100

做这道题目时推荐大家画图感受,更加直观,不容易出现断链的错误,而且图画完了代码也就出来了,这种类型的题目在408选择题中很喜欢考察,请务必重视,养成画图的好习惯,下面给出我个人画的图:

在这里插入图片描述

根据所画的图我们也不难写出对应的代码。

(1)Python版本代码:

# Definition for singly-linked list.
# class ListNode:
#     def __init__(self, val=0, next=None):
#         self.val = val
#         self.next = next
class Solution:def swapPairs(self, head):dummy = ListNode(0)dummy.next = headcur = dummy while cur.next and cur.next.next:# 保存临时节点,避免断链temp1 = cur.next        temp2 = cur.next.nextcur.next = temp2    # 步骤一temp1.next = temp2.next # 步骤二temp2.next = temp1  # 步骤三cur = cur.next.next # 跳两个节点进行下一步操作return dummy.next

(2)C++版本代码:

class Solution {
public:ListNode* swapPairs(ListNode* head) {ListNode* dummy = new ListNode(0);  // 创建一个虚拟头节点dummy->next = head;ListNode* cur = dummy;while (cur->next != nullptr && cur->next->next != nullptr) {// 保存临时节点,避免断链ListNode* temp1 = cur->next;ListNode* temp2 = cur->next->next;cur->next = temp2;        // 步骤一:将 cur 的 next 指向 temp2temp1->next = temp2->next;  // 步骤二:将 temp1 的 next 指向 temp2 的 nexttemp2->next = temp1;      // 步骤三:将 temp2 的 next 指向 temp1cur = cur->next->next;    // 跳两个节点进行下一步操作}ListNode* new_head = dummy->next;delete dummy;  // 删除虚拟头节点return new_head;}
};
  • 时间复杂度:O(n)
  • 空间复杂度:O(1)

2 LeetCode 19.删除链表的倒数第N个节点

题目链接:https://leetcode.cn/problems/remove-nth-node-from-end-of-list/description/

给你一个链表,删除链表的倒数第 n 个结点,并且返回链表的头结点。

示例 1:

在这里插入图片描述

输入:head = [1,2,3,4,5], n = 2
输出:[1,2,3,5]

示例 2:

输入:head = [1], n = 1
输出:[]

示例 3:

输入:head = [1,2], n = 1
输出:[1]

提示:

  • 链表中结点的数目为 sz
  • 1 <= sz <= 30
  • 0 <= Node.val <= 100
  • 1 <= n <= sz

**进阶:**你能尝试使用一趟扫描实现吗?

这道题目的解法跟2009年408数据结构算法题如出一辙,我们在前面的数组学习中也提到了那道题目,如下图所示:

在这里插入图片描述

408的这道题目和力扣的这道题目都是双指针法的经典应用,408的09年算法题只需要查找,而今天这题只是多加了一步删除操作,下面我们首先来解决408的09年的那道算法题。

2.1 2009年408算法题

(1)算法的基本设计思想:问题的关键是设计一个尽可能高效的算法,通过链表的一趟遍历,找到倒数第k个结点的位置。算法的基本设计思想:定义两个指针变量p和q,初始时均指向头结点的下一个结点(链表的第一个结点)。p指针沿链表移动,当p指针移动到第k个结点时,q指针开始与p指针同步移动;当p指针移动到最后一个结点时,q指针所指示结点为倒数第k个结点。以上过程对链表仅进行一遍扫描。

(2)算法的详细实现步骤:

①count=0,p和q指向链表表头结点的下一个结点;

②若p为空,转⑤;

③若count 等于k,则q指向下一个结点;否则,count = count + 1;

④p指向下一个结点,转②;

⑤若count等于k,则查找成功,输出该结点的data域的值,返回1;否则,说明k值超过了线性表的长度,查找失败,返回0;

⑥算法结束。

(3)算法实现:

typedef int ElemType;
typedef struct LNode{ElemType data;struct Lnode *link;
}*LinkList;int Search_k(LinkList list, int k){LinkList p=list->link,q=list->link;int count=0;while(p!=NULL){if(count<k) count++;else q=q->link;p=p->link;}if(count<k)return 0;else{printf("%d",q->data);return 1;}
}

2.2 LeetCode19题

这道题目的思路和上面一样,我们定义两个指针(fast 和 slow)初始都指向虚拟头节点,将 fast 指针向前移动 n 步,这样fast 和 slow 之间保持了 n 个节点的间隔,紧接着同时移动两个指针,直到 fast 指针到达链表末尾(fast.nextNone),此时slow 指针正好指向要删除节点的前一个节点,修改 slow 指针的 next 指向,以跳过需要删除的节点,返回虚拟头节点的下一个节点作为新的头节点

(1)Python版本代码:

class Solution:def removeNthFromEnd(self, head, n):dummy = ListNode(0)  # 创建虚拟头节点dummy.next = headslow = fast = dummy  # 初始化 slow 和 fast 指针# 移动 fast 指针,使其与 slow 之间的间隔为 nwhile(n > 0 and fast):fast = fast.nextn -= 1fast = fast.next# 同时移动 slow 和 fast,直到 fast 到达链表末尾while(fast):fast = fast.nextslow = slow.next# 删除节点slow.next = slow.next.nextreturn dummy.next  # 返回新的头节点

(2)C++版本代码:

class ListNode {
public:int val;ListNode *next;ListNode(int x) : val(x), next(nullptr) {}
};class Solution {
public:ListNode* removeNthFromEnd(ListNode* head, int n) {ListNode* dummy = new ListNode(0);  // 创建一个虚拟头节点dummy->next = head;ListNode* slow = dummy;ListNode* fast = dummy;// 移动 fast 指针,使其与 slow 之间的间隔为 nwhile (n > 0) {fast = fast->next;n--;}fast = fast->next;// 同时移动 slow 和 fast,直到 fast 到达链表末尾while (fast) {fast = fast->next;slow = slow->next;}// 删除节点ListNode* temp = slow->next;slow->next = slow->next->next;delete temp;  // 释放被删除节点的内存ListNode* newHead = dummy->next;delete dummy;  // 删除虚拟头节点,释放内存return newHead;  // 返回新的头节点}
};
  • 时间复杂度: O(n)
  • 空间复杂度: O(1)

3 LeetCode 面试题 02.07. 链表相交

题目链接:https://leetcode.cn/problems/intersection-of-two-linked-lists-lcci/description/

给你两个单链表的头节点 headAheadB ,请你找出并返回两个单链表相交的起始节点。如果两个链表没有交点,返回 null

图示两个链表在节点 c1 开始相交**:**

在这里插入图片描述

题目数据 保证 整个链式结构中不存在环。

注意,函数返回结果后,链表必须 保持其原始结构

示例 1:

在这里插入图片描述

输入:intersectVal = 8, listA = [4,1,8,4,5], listB = [5,0,1,8,4,5], skipA = 2, skipB = 3
输出:Intersected at '8'
解释:相交节点的值为 8 (注意,如果两个链表相交则不能为 0)。
从各自的表头开始算起,链表 A 为 [4,1,8,4,5],链表 B 为 [5,0,1,8,4,5]。
在 A 中,相交节点前有 2 个节点;在 B 中,相交节点前有 3 个节点。

示例 2:

在这里插入图片描述

输入:intersectVal = 2, listA = [0,9,1,2,4], listB = [3,2,4], skipA = 3, skipB = 1
输出:Intersected at '2'
解释:相交节点的值为 2 (注意,如果两个链表相交则不能为 0)。
从各自的表头开始算起,链表 A 为 [0,9,1,2,4],链表 B 为 [3,2,4]。
在 A 中,相交节点前有 3 个节点;在 B 中,相交节点前有 1 个节点。

示例 3:

在这里插入图片描述

输入:intersectVal = 0, listA = [2,6,4], listB = [1,5], skipA = 3, skipB = 2
输出:null
解释:从各自的表头开始算起,链表 A 为 [2,6,4],链表 B 为 [1,5]。
由于这两个链表不相交,所以 intersectVal 必须为 0,而 skipA 和 skipB 可以是任意值。
这两个链表不相交,因此返回 null 。

提示:

  • listA 中节点数目为 m
  • listB 中节点数目为 n
  • 0 <= m, n <= 3 * 104
  • 1 <= Node.val <= 105
  • 0 <= skipA <= m
  • 0 <= skipB <= n
  • 如果 listAlistB 没有交点,intersectVal0
  • 如果 listAlistB 有交点,intersectVal == listA[skipA + 1] == listB[skipB + 1]

**进阶:**你能否设计一个时间复杂度 O(n) 、仅用 O(1) 内存的解决方案?

这道面试题目也在408的考试中出现过了,也就是2012年的408算法题,也和这题如出一辙,同样的思路同样的解决办法,下面我贴出2012年的408算法题给大家看看。

3.1 2012年408算法题

在这里插入图片描述

下面我给出王道官方答案:

在这里插入图片描述

3.2 LeetCode 面试题 02.07题

看完408的题目是不是觉得和今天的题目基本一模一样,我也挺感叹的,所以还是要好好刷题,现在我们回到力扣的题目,题目要我们求出链表交点,也就是求两个链表交点节点的指针,需要注意的是交点不是数值相等,而是指针相等,在上面的王道官方答案里面也说过,所以需要留意一下,避免出错。

我们仿照上面王道的思路,首先分别计算两个链表的长度,这一步是为了确定哪个链表更长,以及它们长度的差异,然后根据两个链表的长度差,调整较长链表的起始位置,这意味着,如果一个链表比另一个长,我们就将较长链表的头部向前移动直到两个链表从同一长度开始,也就是尾部对齐操作,接着从这个相同长度的起点开始,同时遍历两个链表,由于两个链表现在是同步的,如果它们相交,那么它们必定会在某个点拥有相同的节点,继续同步遍历直到找到两个链表相同的节点,这个节点就是交点。如果没有交点,则最终两个指针都会同时到达各自链表的末尾。

(1)Python版本代码:

class Solution:def getIntersectionNode(self, headA: ListNode, headB: ListNode) -> ListNode:# 获取链表的长度def getLength(head):length = 0while head:length += 1head = head.nextreturn lengthlenA, lenB = getLength(headA), getLength(headB)  # 计算两个链表的长度# 根据长度差,调整两个链表的起始位置while lenA > lenB:headA = headA.nextlenA -= 1while lenB > lenA:headB = headB.nextlenB -= 1# 同步遍历两个链表,直到找到相交节点while headA != headB:headA = headA.nextheadB = headB.nextreturn headA  # 相交节点(如果不存在则为 None)

(2)C++版本代码:

class Solution {
public:// 获取链表的长度int getLength(ListNode* head) {int length = 0;while (head != NULL) {length++;head = head->next;}return length;}// 找到两个链表的相交节点ListNode* getIntersectionNode(ListNode* headA, ListNode* headB) {int lenA = getLength(headA);  // 链表A的长度int lenB = getLength(headB);  // 链表B的长度// 根据长度差,调整两个链表的起始位置while (lenA > lenB) {headA = headA->next;lenA--;}while (lenB > lenA) {headB = headB->next;lenB--;}// 同步遍历两个链表,直到找到相交节点while (headA != headB) {headA = headA->next;headB = headB->next;}return headA;  // 相交节点(如果不存在则为 nullptr)}
};
  • 时间复杂度:O(n + m)
  • 空间复杂度:O(1)

4 LeetCode 142.环形链表II

题目链接:https://leetcode.cn/problems/linked-list-cycle-ii/description/

给定一个链表的头节点 head ,返回链表开始入环的第一个节点。 如果链表无环,则返回 null

如果链表中有某个节点,可以通过连续跟踪 next 指针再次到达,则链表中存在环。 为了表示给定链表中的环,评测系统内部使用整数 pos 来表示链表尾连接到链表中的位置(索引从 0 开始)。如果 pos-1,则在该链表中没有环。注意:pos 不作为参数进行传递,仅仅是为了标识链表的实际情况。

不允许修改 链表。

示例 1:

在这里插入图片描述

输入:head = [3,2,0,-4], pos = 1
输出:返回索引为 1 的链表节点
解释:链表中有一个环,其尾部连接到第二个节点。

示例 2:

在这里插入图片描述

输入:head = [1,2], pos = 0
输出:返回索引为 0 的链表节点
解释:链表中有一个环,其尾部连接到第一个节点。

示例 3:

在这里插入图片描述

输入:head = [1], pos = -1
输出:返回 null
解释:链表中没有环。

提示:

  • 链表中节点的数目范围在范围 [0, 104]
  • -105 <= Node.val <= 105
  • pos 的值为 -1 或者链表中的一个有效索引

**进阶:**你是否可以使用 O(1) 空间解决此题?

这道题目强烈推荐去看一下卡哥的视频讲解以及文字讲解,算是全网讲解最详细,卡哥的代码随想录关于这道题目有很多图解,大家可以去看看,由于我最近在忙于课设验收工作,所以在此就简单介绍一下两种实现思路。

4.1 快慢指针

我们使用两个指针,一个快指针(每次移动两步)和一个慢指针(每次移动一步),如果链表中存在环,快慢指针最终会在环内相遇(这里涉及一个数学推导,差不多中学知识就可以理解),找到相遇点后,将一个指针移回链表头部,另一个保持在相遇点,两个指针每次都移动一步,当它们再次相遇时,相遇点就是环的起始节点。

(1)Python版本代码

class Solution:def detectCycle(self, head: Optional[ListNode]) -> Optional[ListNode]:if not head:return Noneslow, fast = head, headhas_cycle = False# 使用快慢指针检测环while fast and fast.next:slow = slow.nextfast = fast.next.nextif slow == fast:has_cycle = Truebreak# 如果存在环,找到环的起点if has_cycle:slow = head  # 将一个指针移回链表头部while slow != fast:  # 当两个指针再次相遇时,即为环的起点slow = slow.nextfast = fast.nextreturn slowreturn None  # 如果没有环,返回 None

(2)C++版本代码

class ListNode {
public:int val;ListNode *next;ListNode(int x) : val(x), next(nullptr) {}
};class Solution {
public:ListNode *detectCycle(ListNode *head) {if (head == nullptr || head->next == nullptr) {return nullptr;}ListNode *slow = head;ListNode *fast = head;bool hasCycle = false;// 使用快慢指针检测环while (fast != nullptr && fast->next != nullptr) {slow = slow->next;fast = fast->next->next;if (slow == fast) {hasCycle = true;break;}}// 如果存在环,找到环的起点if (hasCycle) {slow = head;  // 将一个指针移回链表头部while (slow != fast) {  // 当两个指针再次相遇时,即为环的起点slow = slow->next;fast = fast->next;}return slow;}return nullptr;  // 如果没有环,返回 nullptr}
};
  • 时间复杂度:O(N),这里 N 是链表的节点数,在最坏的情况下,我们需要遍历整个链表一次来确定环的起点或确认链表没有环。
  • 空间复杂度:O(N),需要额外的空间来存储已经访问过的节点,在最坏的情况下可能需要将整个链表的节点都存储在哈希表中。

4.2 哈希表

哈希表方法也算比较简单,大致思路就是遍历链表,同时将每个节点存入哈希表,每次遍历时,检查当前节点是否已存在于哈希表中,如果当前节点已存在于哈希表,说明找到了环的起点;否则,继续遍历,如果遍历完链表都没有找到环,返回 None

(1)Python版本代码

class Solution:def detectCycle(self, head: Optional[ListNode]) -> Optional[ListNode]:visited = set()  # 创建哈希表来存储访问过的节点while head:if head in visited:  # 检查节点是否出现过return head      # 找到环的起点visited.add(head)   # 将节点添加到哈希表head = head.nextreturn None  # 没有环

(2)C++版本代码

class ListNode {
public:int val;ListNode *next;ListNode(int x) : val(x), next(nullptr) {}
};class Solution {
public:ListNode *detectCycle(ListNode *head) {unordered_set<ListNode*> visited;  // 哈希表存储访问过的节点while (head != nullptr) {if (visited.count(head))  // 检查节点是否已在哈希表中return head;  // 找到环的起点visited.insert(head);  // 将节点加入哈希表head = head->next;}return nullptr;  // 没有环}
};
  • 时间复杂度:O(N),虽然快指针比慢指针移动得快,但在最坏的情况下,时间复杂度仍然是 O(N),这是因为快指针最多遍历整个链表两次(第一次是找到相遇点,第二次是与慢指针一起找到环的起点)。
  • 空间复杂度:O(1),这种方法只需要常数级别的额外空间,因为它只使用了两个指针(快指针和慢指针),而不需要存储其他额外的信息。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/237049.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

软件测试|教你使用Python绘制正多边形

简介 绘制正多边形是Python图形编程的基本任务之一。在本文中&#xff0c;我将为你提供一个使用Python绘制正多边形的详细教程&#xff0c;并提供一个示例代码。我们将使用Python的Turtle库来进行绘制。 步骤1&#xff1a;导入Turtle库 我们需要先安装好Python环境&#xff…

【信息安全】深度分析邮件安全及钓鱼攻击防范

本博文共计3100余字&#xff0c;预计需阅读20分钟 【邮件安全建设】 一、前言 邮件系统作为企业办公网络架构中重要的组成部分&#xff0c;同时也是业务高频使用的办公应用&#xff0c;一旦出现安全问题&#xff0c;业务将会被严重干扰甚至中断&#xff0c;本篇博客通过攻守两…

软件测试|Python数据可视化神器——pyecharts教程(十)

使用pyecharts绘制漏斗图 简介 漏斗图&#xff08;Funnel Chart&#xff09;是一种用于可视化数据流程或转化率的图表类型。它通常由一系列阶段组成&#xff0c;每个阶段都有一个名称和一个值&#xff0c;表示在该阶段的转化量或数据流程的进展情况。漏斗图的名称来源于其外观…

浅析五种 React 组件设计模式

作为一名 React 开发者&#xff0c;你可能会面临下面几个问题&#xff1a; 如何构建一个高复用度性的组件&#xff0c;使其适应不同的业务场景&#xff1f;如何构建一个具有简单 API的组件&#xff0c;使其易于使用&#xff1f;如何构建一个在 UI 和功能方面具有可扩展性的组件…

[C#]使用winform部署PP-MattingV2人像分割onnx模型

【官方框架地址】 https://github.com/PaddlePaddle/PaddleSeg 【算法介绍】 PP-MattingV2是一种先进的图像和视频抠图算法&#xff0c;由百度公司基于PaddlePaddle深度学习框架开发。它旨在提供更精准和高效的图像分割功能&#xff0c;特别是在处理图像中的细微部分&#xf…

set -e的作用

今天看人家代码看到一个很有意思的命令 后面我搜索了一下&#xff0c;感觉还是很好用的 set -e 是一个调试用的好东西 比如test.sh echo "执行第一个命令" cd /aaa/bbb echo "执行第二个命令"结果如下 可以看到第二个命令是执行了&#xff0c;虽然我的第…

利用C语言实现输出杨辉三角的前10行

杨辉三角的特点 第一列都为1&#xff0c;对角线为1 第x行第x列为1 第几行就有几个元素 从第三行开始,第二列的元素等于第二行的第一列元素第二列元素之和(排除从第三行开始的首和尾元素) //用C语言实现打印出10行杨辉三角 #include<stdio.h>int main(){int a[10][10];//…

使用RNN完成IMDB电影评论情感分析

使用RNN完成IMDB电影评论情感分析 任务描述一、环境设置二、数据准备2.1 参数设置2.2 用padding的方式对齐数据2.3 用Dataset与DataLoader加载三、模型配置四、模型训练五、模型评估六、模型预测 任务描述 本示例教程演示如何在IMDB数据集上使用RNN网络完成文本分类的任务。IM…

二极管限幅电路理论分析,工作原理+作用

一、限幅是什么意思&#xff1f; 限幅也就是&#xff0c;将电压限制在某个范围内&#xff0c;去除交流信号的一部分但不会对波形的剩余部分造成影响。通常来说&#xff0c;限幅电路主要是由二极管构成&#xff0c;波形的形状取决于电路的配置和设计。二、限幅电路工作原…

x-cmd pkg | busybox - 嵌入式 Linux 的瑞士军刀

目录 简介首次用户功能特点竞品和相关作品 进一步阅读 简介 busybox 是一个开源的轻量级工具集合&#xff0c;集成了一批最常用 Unix 工具命令&#xff0c;只需要几 MB 大小就能覆盖绝大多数用户在 Linux 的使用&#xff0c;能在多款 POSIX 环境的操作系统&#xff08;如 Linu…

Vulnhub靶机:driftingblues 3

一、介绍 运行环境&#xff1a;Virtualbox 攻击机&#xff1a;kali&#xff08;10.0.2.15&#xff09; 靶机&#xff1a;driftingblues3&#xff08;10.0.2.19&#xff09; 目标&#xff1a;获取靶机root权限和flag 靶机下载地址&#xff1a;https://www.vulnhub.com/entr…

WebGL在实验室方向的应用

WebGL在实验室方向的应用涉及到实验过程的可视化、数据分析、模拟等方面。以下是一些WebGL在实验室领域的应用示例&#xff0c;希望对大家有所帮助。北京木奇移动技术有限公司&#xff0c;专业的软件外包开发公司&#xff0c;欢迎交流合作。 1.分子模型和化学反应模拟&#xff…

D25XB80-ASEMI开关电源桥堆D25XB80

编辑&#xff1a;ll D25XB80-ASEMI开关电源桥堆D25XB80 型号&#xff1a;D25XB80 品牌&#xff1a;ASEMI 封装&#xff1a;GBJ-5&#xff08;带康铜丝&#xff09; 特性&#xff1a;插件、整流桥 平均正向整流电流&#xff08;Id&#xff09;&#xff1a;25A 最大反向击…

C++笔记

1.输入输出流 在C中要想输入和输出 我们会经常用到 #include <stdio.h>在C中头文件的命名风格不用.h #include <iostream>using namespace std;为什么要用上面俩句话的解释&#xff08;自己写的博客&#xff09; c中 为什么要写&#xff1c;iostream&#xff1e;…

数模学习day13-典型相关分析

典型相关分析&#xff08;Canonical Correlation analysis&#xff09; 研究两组变量&#xff08;每组变量中都可能有多个指标&#xff09;之间相关关系的一种多元统计方法。它能够揭示出两组变量之间的内在联系。 注&#xff1a;本文源于数学建模学习交流相关公众号观…

使用JGit拉取代码提示未授权not authorized

原因&#xff1a;2021年8月13日后不支持密码登录&#xff0c;需要使用token验证 调用时候需要先去git仓库创建个人令牌 需要在安全中心创建个人token&#xff0c;使用token名称作为账号&#xff0c;使用token作为密码。 另&#xff1a; Github克隆仓库的三种方式对比&#xff…

哪里能找到好用的PPT模板?12个免费模板网站让你畅快办公!

你是否有过这样的经历&#xff0c;在准备重要会议或者演讲的时候&#xff0c;为找不到合适的PPT模板而困扰&#xff1f;或是在网上漫无目的地搜寻&#xff0c;结果收获的是设计平淡无奇的PPT模板&#xff1f; 如果你有同样的疑问&#xff0c;那么你来对地方了&#xff01;在这…

基于嵌入式的智能台灯系统

基于嵌入式的智能台灯系统 功能说明 通过微信小程序控制台灯的亮灭及亮度。采集温湿度传到微信小程序上&#xff0c;台灯可以显示实时北京时间。 功能展示 01智能台灯演示 Mqtt服务器 http://www.yoyolife.fun/iot&#xff1a;Mqtt服务器&#xff0c;我是在这里注册的&#x…

WPF实现右键选定TreeViewItem

在WPF中&#xff0c;TreeView默认情况是不支持右键选定的&#xff0c;也就是说&#xff0c;当右键点击某节点时&#xff0c;是无法选中该节点的。当我们想在TreeViewItem中实现右键菜单时&#xff0c;往往希望在弹出菜单的同时选中该节点&#xff0c;以使得菜单针对选中的节点生…

程序员如何弯道超车?周末有奇效

作为一名程序员&#xff0c;不断提升自己的技能和知识是至关重要的。然而&#xff0c;在繁忙的工作日常中&#xff0c;很难有足够的时间和精力来学习新技术或深入研究。因此&#xff0c;周末成为了一个理想的时机&#xff0c;可以专注于个人发展和技能提升。所以程序员如何利用…