当前位置: 首页 > news >正文

CD73.【C++ Dev】map和set练习题1(有效的括号、复杂链表的复制)

目录

1.有效的括号

分析

代码

提交结果

2.复杂链表的复制

分析

代码

提交结果

​编辑


1.有效的括号

之前在L11.【LeetCode题解】有效的括号文章用C语言写过,要求采用C++ STL优化以下代码:

typedef char STDataType;
typedef struct Stack
{STDataType* a;int top; int capacity;
}ST;void STInit(ST* ps)
{assert(ps);ps->a = (STDataType*)malloc(sizeof(STDataType) * 4);if (ps->a == NULL){perror("malloc");return;}ps->capacity = 4;ps->top = 0;//top栈顶元素的下一个位置
}void STDestory(ST* ps)
{assert(ps);free(ps->a);ps->a = NULL;ps->top = 0;ps->capacity = 0;
}void STPush(ST* ps, STDataType x)
{assert(ps);if (ps->top == ps->capacity){STDataType* tmp = (STDataType*)realloc(ps->a, sizeof(STDataType) * ps->capacity * 2);if (tmp == NULL){perror("realloc");return;}ps->a = tmp;ps->capacity *= 2;}ps->a[ps->top] = x;ps->top++;
}bool STEmpty(ST* ps)
{assert(ps);return ps->top == 0;
}
void STPop(ST* ps)
{assert(ps);assert(!STEmpty(ps));//确保不越界ps->top--;
}STDataType STTop(ST* ps)//访问栈顶元素
{assert(ps);assert(!STEmpty(ps));//确保不越界return ps->a[ps->top - 1];
}bool isValid(char* s) 
{ST st;STInit(&st);while(*s){if (*s=='('||*s=='['||*s=='{'){STPush(&st,*s);}else{if (STEmpty(&st))return false;char top=STTop(&st);//注意STPop(&st);if ((*s==')'&&top !='(')||(*s==']'&&top !='[')||(*s=='}'&&top !='{'))return false;}s++;}bool ret=STEmpty(&st);STDestory(&st);return ret;
}

分析

上方代码手动实现了栈的各个操作,可以改用STL的stack<char>

class Solution {
public:bool isValid(string s) {stack<char> st;for (auto ch:s){if (ch=='('||ch=='['||ch=='{'){st.push(ch);}else{if (st.empty())return false;char top=st.top();st.pop();if ((ch==')'&&top !='(')||(ch==']'&&top !='[')||(ch=='}'&&top !='{'))return false;}}return st.empty();}
};

本题考察括号的匹配,匹配问题可以用map,那么if判断可以用map优化

map中存储正确的匹配:

map<char,char> mp;
//调用operator[]比用insert写起来方便
mp['(']=')';
mp['[']=']';
mp['{']='}';

简化if判断:

if (mp.count(ch))//如果ch能在map的所有key中能找到,就push
{st.push(ch);
}
else
{if (st.empty())return false;char top=st.top();st.pop();if (mp[top]!=ch)//左右括号不匹配,返回falsereturn false;
}

代码

class Solution {
public:bool isValid(string s) {stack<char> st;map<char,char> mp;//调用operator[]比用insert写起来方便mp['(']=')';mp['[']=']';mp['{']='}';for (auto ch:s){if (mp.count(ch))//如果ch能在map的所有key中能找到,就push{st.push(ch);}else{if (st.empty())return false;char top=st.top();st.pop();if (mp[top]!=ch)//左右括号不匹配,返回falsereturn false;}}return st.empty();}
};

提交结果

2.复杂链表的复制

之前在L34.【LeetCode题解】随机链表的复制(复杂链表的复制)文章用C语言写过,要求采用C++ STL优化以下代码:

struct Node* copyRandomList(struct Node* head) 
{struct Node* cur=head;//插入新节点while(cur){struct Node* newnode=(struct Node*)malloc(sizeof(struct Node));newnode->next=cur->next;newnode->val=cur->val;cur->next=newnode;cur=cur->next->next;}//设置randomcur=head;while(cur){struct Node* copy=cur->next;if (cur->random==NULL){copy->random=NULL;}else{copy->random=cur->random->next;//重要的一步}cur=cur->next->next;}struct Node* copy_head=NULL;struct Node* copy_tail=NULL;cur=head;while(cur){struct Node* copy=cur->next;struct Node* copy_next=copy->next;if (copy_head==NULL)//空链表尾插{copy_head=copy_tail=copy;}else//非空链表尾插{copy_tail->next=copy;copy_tail=copy_tail->next;//更新尾部}cur->next=copy_next;//恢复原链表cur=cur->next;}return copy_head;   
}

分析

首先复制链表,暂时`不处理random指针

if (head==nullptr)return nullptr;
Node* cur=head;//遍历要复制的链表
Node* copy=nullptr;
Node* copy_head=nullptr;//保存拷贝链表的头节点
for(;;)
{if (copy==nullptr){copy=new Node(cur->val);copy_head=copy;cur=cur->next;}else if (cur){copy->next=new Node(cur->val);copy=copy->next;cur=cur->next;}else//复制完毕break;
}

链表复制中比较难处理的是random指针指向的节点,处理方法: 用map提前存映射,让cur指向的节点和copy指向的节点一一对应

那么在设置random时:

解读图片: cur指向的节点的random的值为cur->random,指向的节点对应在新链表中的位置为map[cur->random],这下copy->random就好设置值了

那么可以边复制链表(不包含设置random指针)边设置map<Node*,Node*>:

if (head==nullptr)return nullptr;
Node* cur=head;//遍历要复制的链表
Node* copy=nullptr;
Node* copy_head=nullptr;//保存拷贝链表的头节点
map<Node*,Node*> mp;
for(;;)
{if (copy==nullptr){copy=new Node(cur->val);mp[cur]=copy;copy_head=copy;cur=cur->next;}else if (cur){copy->next=new Node(cur->val);copy=copy->next;mp[cur]=copy;cur=cur->next;}else//复制完毕break;
}

最后依据map的内容设置复制链表的指针:

//设置random
copy=copy_head;
cur=head;
while(copy)
{copy->random=mp[cur->random];cur=cur->next;copy=copy->next;
}

代码

class Solution {
public:Node* copyRandomList(Node* head) {if (head==nullptr)return nullptr;Node* cur=head;//遍历要复制的链表Node* copy=nullptr;Node* copy_head=nullptr;//保存拷贝链表的头节点map<Node*,Node*> mp;for(;;){if (copy==nullptr){copy=new Node(cur->val);mp[cur]=copy;copy_head=copy;cur=cur->next;}else if (cur){copy->next=new Node(cur->val);copy=copy->next;mp[cur]=copy;cur=cur->next;}else//复制完毕break;}//设置randomcopy=copy_head;cur=head;while(copy){copy->random=mp[cur->random];cur=cur->next;copy=copy->next;}return copy_head;}
};

提交结果

http://www.dtcms.com/a/359881.html

相关文章:

  • 嵌入式C学习笔记之编码规范
  • Nginx实现P2P视频通话
  • 现代C++特性 并发编程:线程管理库 <thread>(C++11)
  • 狂神说--Nginx--通俗易懂
  • 【秋招笔试】2025.08.31饿了么秋招笔试题
  • Linux基本工具(yum、vim、gcc、Makefile、git、gdb)
  • 苏宁移动端部分首页制作
  • ing Data JPA 派生方法 数据操作速查表
  • TFS-1996《The Possibilistic C-Means Algorithm: Insights and Recommendations》
  • Kafka面试精讲 Day 3:Producer生产者原理与配置
  • K8s学习笔记(一)——
  • Unity转抖音小游戏重点摘记
  • 通信原理(006)——分贝(dB)超级详细
  • 【数学史冷知识】关于行列式的发展史
  • spring-ai-alibaba-deepresearch 学习(七)——源码学习之PlannerNode
  • (树)Leetcode94二叉树的中序遍历
  • 8.29学习总结
  • YOLO 目标检测:YOLOv2基本框架、多尺度训练、锚框、维度聚类、位置预测、passthrough
  • 【机器学习基础】无监督学习算法的现代演进:从数据探索到智能系统的自主发现能力
  • hardhat 3 测试框架选择
  • 十分钟快速掌握 YML YAML 文件
  • LLM记账智能体-MCP服务-实现步骤与效果展示
  • Qt精华版打包教程,支持windows和Linux,每种平台支持2种方案
  • MCP SDK 示例一
  • Spring MVC 九大组件源码深度剖析(六):HandlerExceptionResolver - 异常处理的艺术
  • 第八章 光照
  • 蓝牙AOA智慧仓储管理系统:实现仓储数字化升级的精准定位解决方案
  • 解决IDEA 2025.2升级报错:Scannning Files to Index卡住问题分析与修复
  • python复杂代码如何让ide自动推导提示内容
  • 【系列12】端侧AI:构建与部署高效的本地化AI模型 第11章:边缘设备与IoT部署