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

go 链表 (标准库实现)

Go 链表简介Go 标准库里没有单链表只在 container/list 包里提供了双向循环链表。两个核心类型list.List 链表本身包含哨兵节点和长度list.Element 链表节点存数据 前后指针type Element struct { Value interface{} // 节点数据 (任意类型) // next, prev 是私有字段不能直接访问 }特点• 双向每个节点有 Next() 和 Prev()支持双向遍历• 循环内部用一个哨兵节点串成环首尾相连所以代码里没有 nil 判断的边界 case操作非常简洁• Value 是 interface{}可以存任意类型但取出来要类型断言e.Value.(int)• Len() 是 O(1)内部维护了计数不需要遍历常用方法速查遍历模板package main import ( container/list fmt ) func main() { // 创建一个新的链表 l : list.New() // 在链表的尾部添加元素 l.PushBack(Go) l.PushBack(is) l.PushBack(awesome) // 在链表的头部添加元素 l.PushFront(Programming) // 遍历链表并打印元素 for e : l.Front(); e ! nil; e e.Next() { fmt.Println(e.Value) } }几个坑1. Value 类型断言e.Value.(int)类型错了会 panic2. 查找是 O(n)链表没有按值查找的 API得自己写循环 → 这就是为什么 LRU 要配一个 map 做索引3. 节点必须先拿到 *list.Element 才能操作Remove / InsertBefore / MoveToFront 都接收节点指针不接收值4. 不要跨链表移动节点l1 的节点别拿去 l2.Remove()行为未定义什么时候用 container/list• ✅ 需要频繁在中间插入/删除且已经持有节点指针LRU 缓存、任务调度队列• ❌ 只是顺序存取 / 随机访问 → 直接用 slicecache 友好性吊打链表99% 的场景用 slice 就够了剩下 1% 才考虑 container/list。LRU 示例package main import ( container/list fmt ) // 实现一个LRU缓存策略缓存满了就淘汰最久没使用的那个 type LRUCache struct { capability int ll *list.List cache map[int]*list.Element } type entry struct { key, value int } func Constructor(capability int) LRUCache { return LRUCache{ capability: capability, ll: list.New(), cache: make(map[int]*list.Element), } } // 存元素如果元素已经存在则更新放到头部 // 如果元素不存在则加到头部然后判断是否溢出。 func(c *LRUCache) Put(key, value int) { if e,ok : c.cache[key]; ok{ e.Value.(*entry).value value c.ll.MoveToFront(e) return } e : c.ll.PushFront(entry{key: key, value: value}) c.cache[key] e if c.ll.Len() c.capability { e : c.ll.Back() delete(c.cache, e.Value.(*entry).key) c.ll.Remove(e) } } // 获取元素如果元素存在放回并放回头部如果不存在返回-1 func(c *LRUCache) Get(key int) int { if e, ok : c.cache[key]; ok { c.ll.MoveToFront(e) return e.Value.(*entry).value } return -1 } func main() { lrucache : Constructor(2) lrucache.Put(1,3) lrucache.Put(1,4) lrucache.Put(2,9) for e:lrucache.ll.Front(); e!nil;ee.Next() { fmt.Println(e.Value.(*entry).value) } }QA1:为什么用指针接收者 c *LRUCache因为方法里要修改 c 的内部状态链表、map用值接收者会改了个寂寞。对比// 值接收者c 是副本改了不影响原对象 func (c LRUCache) Put(...) { c.ll.PushFront(...) } // 看起来生效了 // 指针接收者c 指向原对象改的就是它本身 func (c *LRUCache) Put(...) { c.ll.PushFront(...) } // ✅ 真正生效⚠️ 有个细节ll 本身是 *list.List指针所以值接收者下 PushFront居然也看似能改链表——因为副本和原对象共享同一个底层链表。但 capacity 这种字段就改不动了而且 map 操作也会出问题。不要依赖这种巧合。Go 的两条经验法则1. 方法里要改字段 → 必须用指针接收者2. 结构体比较大、或包含 mutex/slice/map → 也建议用指针避免拷贝、避免锁失效3. 同一个类型的所有方法接收者类型要统一要么都是值要么都是指针否则方法集混乱、接口实现也容易踩坑LRU 三条全占要改状态、含 map 和 list、需要保持一致 → 必须是 *LRUCache。QA2: *list.List为什么是指针因为list.New()返回指针QA3: *list.Element 为什么这个也是指针呢因为 container/list 里所有方法本来就要求传 *list.Elementmap 存指针只是顺手保持一致避免来回取址。看 list 包的 API 签名func (l *List) PushFront(v any) *list.Element // 返回的就是指针 func (l *List) MoveToFront(e *list .Element) // 接收指针 func (l *List) Remove(e *list.Element) any // 接收指针 func (l *List) InsertBefore(v any, mark *list.Element) // 接收指针Go 标准库设计上链表节点天生就是用指针在传递的。所以elem : c.ll.PushFront(...) // elem 已经是 *list.Element c.cache[key] elem // 直接塞 map类型匹配如果存值类型每次用还得 v自找麻烦。QA4: *list.List不是一个双向链表吗一直next()为什么会出现nil呢container/list 的实现确实是循环双向链表内部有一个哨兵节点root最后一个节点的 next 指向 rootroot 的 next 又指向第一个节点。但是 Next() 和 Prev() 这两个公开方法被故意做了处理当下一个节点是 root 哨兵节点时返回 nil而不是把这个内部节点暴露出来。标准库源码src/container/list/list.gofunc (e *Element) Next() *Element { if p : e.next; e.list ! nil p ! e.list.root { return p } return nil } func (e *Element) Prev() *Element { if p : e.prev; e.list ! nil p ! e.list.root { return p } return nil }关键就是 p ! e.list.root 这个判断——一旦走到 root 哨兵就返回 nil。所以• 内部数据结构循环双向链表用 root 哨兵简化插入/删除的边界判断不需要处理 head/tail 为 nil 的特殊情况。• 对外暴露的迭代接口非循环到末尾返回 nil符合 Go 的习惯写法

相关文章:

go 链表 (标准库实现)

Go 链表简介Go 标准库里没有单链表,只在 container/list 包里提供了双向循环链表。两个核心类型list.List :链表本身,包含哨兵节点和长度 list.Element :链表节点,存数据 前后指针 type Element struct {Value interf…...

Linux 系统编程 文件篇 (二)

[TOC] Linux 系统编程 文件篇 (二) 1 open 函数介绍 1.1 标记位 上一篇的结尾,我们讲到了我们用的打开文件的库函数其实是封装了,这个 open 的系统调用,然后解释了这个 open 函数的 这个标记位,flags 是一个…...

标题:【2026 最全】CTF 零基础入门指南|小白必看,一篇封神!

前言 CTF(Capture The Flag)中文一般译作夺旗赛,在网络安全领域中指的是网络安全技术人员之间进行技术竞技的一种比赛形式。发展至今,已经成为全球范围网络安全圈流行的竞赛形式,而DEFCON作为CTF赛制的发源地&#xf…...

【2026 最新】Web 安全完整学习指南 红队全套技能栈

0x00 技能栈 依照红队的流程分工,选择适合自己的技能栈发展。 越接近中心的能力点越贴近web技术栈,反之亦然。可以根据自身情况,选择技术栈的发展方向。 0x01 漏洞理解篇(Vulnerability) 1.1 前端 同源策略 & CSP & JOSNP 跨域…...

LabVIEW项目实战:用‘类+队列’模式管理仪器参数,告别全局变量混乱

LabVIEW工程实践:基于类与队列的仪器参数管理框架设计 在工业自动化测试系统中,仪器参数管理一直是困扰工程师的典型难题。当系统需要同时控制网口、串口、GPIB等多种接口的测试设备时,传统的全局变量方案会导致参数耦合、修改不同步等问题。…...

【MATLAB源码-第439期】基于MATLAB的APSK与QAM高阶调制在Saleh非线性功放下BER和EVM性能对比

操作环境:MATLAB 2024a1、算法描述摘要 高阶数字调制技术是现代无线通信和卫星通信系统提高频谱利用率的重要方法。QAM 调制通过同相分量和正交分量的幅度组合形成二维星座,在较高信噪比条件下能够获得较高的信息承载能力。APSK 调制则采用多环幅相结构&…...

3个真实场景告诉你,Avogadro 2分子建模软件如何改变化学研究方式

3个真实场景告诉你,Avogadro 2分子建模软件如何改变化学研究方式 【免费下载链接】avogadroapp Avogadro is an advanced molecular editor designed for cross-platform use in computational chemistry, molecular modeling, bioinformatics, materials science, …...

JoyCon-Driver:Windows平台上的Switch手柄完美解决方案

JoyCon-Driver:Windows平台上的Switch手柄完美解决方案 【免费下载链接】JoyCon-Driver A vJoy feeder for the Nintendo Switch JoyCons and Pro Controller 项目地址: https://gitcode.com/gh_mirrors/jo/JoyCon-Driver 还在为Nintendo Switch JoyCon控制器…...

西南交通大学【数电实验之Modelsim仿真全流程实战】

1. 从零开始搭建Modelsim仿真环境 第一次接触数字电路仿真的同学可能会觉得Modelsim界面复杂,其实只要跟着步骤一步步操作,半小时就能跑通第一个仿真案例。我当年在西南交大做数电实验时,也经历过从一脸懵到熟练操作的过程,这里把…...

利欧股份持续推进“制造业+科技投资”战略 主业与投资协同效应显现

全球商业航天企业SpaceX(太空探索技术公司)计划于6月12日在纳斯达克上市,股票代码为SPCX。此次IPO预计融资规模约为800亿美元,市场估值在1.75万亿至2万亿美元之间,引发资本市场广泛关注。据悉,利欧股份&…...

OpenClaw用户如何通过CLI子命令快速完成Taotoken接入配置

🚀 告别海外账号与网络限制!稳定直连全球优质大模型,限时半价接入中。 👉 点击领取海量免费额度 OpenClaw用户如何通过CLI子命令快速完成Taotoken接入配置 对于使用OpenClaw进行AI智能体开发的开发者而言,快速接入稳定…...

HarmonyOS ArkWeb 系列之网页秒变PDF:createPdf 完整指南

文章目录createPdf 是什么配置参数说清楚Callback 方式Promise 方式完整流程图那个最容易忽略的坑权限配置写在最后能把一张网页直接转成 PDF,保存到本地——这个需求在报表、电子凭证、文档生成场景里非常常见。HarmonyOS 的 Web 组件内置了 createPdf 接口&#x…...

别再只盯着原理图了!FPGA/SoC硬件工程师必看的RGMII接口PCB布线实战指南(含时序约束与等长规则)

RGMII接口PCB设计实战:从时序规范到千兆以太网稳定通信 在FPGA和SoC硬件开发中,RGMII接口设计一直是工程师们又爱又恨的挑战。爱它的简洁高效——相比GMII接口减少了近一半的引脚数量;恨它的时序敏感——一个看似微小的PCB布线失误就可能导致…...

HarmonyOS ArkWeb 系列之从框架层锁死复制权限:copyOptions 详解

文章目录copyOptions 是什么完整代码示例HTML 页面(用于测试)三种模式的实际表现和 H5 层 user-select 的区别实际业务场景踩坑记录写在最后上两篇讲的都是 H5 层面的剪贴板操作。但有些场景下,你需要的不是"监听"或"修改&quo…...

接入 Taotoken 后从账单明细中分析各阶段模型使用占比与成本变化

🚀 告别海外账号与网络限制!稳定直连全球优质大模型,限时半价接入中。 👉 点击领取海量免费额度 接入 Taotoken 后从账单明细中分析各阶段模型使用占比与成本变化 在项目开发中引入大模型能力后,一个常见的困惑是&…...

【Web安全】JWT常见安全漏洞总结

文章目录前言1. JWT基础与漏洞概述2. JWT核心漏洞解析2.1 未校验签名2.1.1 漏洞原理2.1.2 利用方式2.1.3 实战脚本2.2 算法篡改漏洞2.2.1 漏洞原理2.2.2 核心说明2.2.3 攻击流程2.3 弱密钥漏洞2.3.1 漏洞原理2.3.2 利用方式2.4 垂直越权2.4.1 漏洞原理2.4.2 利用流程2.5 KID字段…...

从一次线上故障复盘:如何用 nlohmann::json 的 `value()` 和 `get_to()` 优雅处理缺失字段

从一次线上故障复盘:如何用 nlohmann::json 的 value() 和 get_to() 优雅处理缺失字段 上周五晚上10点,我们的算法服务平台突然收到大量错误告警。一个核心接口在解析上传的算法包时频繁报错,日志里满是[json.exception.type_error.302] type…...

告别手写轮播!用vue-j-scroll插件5分钟搞定Vue列表无缝滚动(含鼠标悬停控制)

5分钟极速集成:用vue-j-scroll实现Vue列表智能滚动方案 在数据密集型的现代Web应用中,动态列表展示几乎成为标配需求。无论是后台管理系统的操作日志、金融平台的实时交易流水,还是新闻客户端的资讯推送,流畅的自动滚动效果不仅能…...

从一次数据解析Bug说起:彻底搞懂QString的toLocal8Bit、toUtf8和toLatin1该用哪个

从一次数据解析Bug说起:彻底搞懂QString的编码转换选择 上周排查一个网络协议解析问题时,遇到一个典型的编码陷阱:服务端返回的GBK编码数据包,在Qt客户端用toUtf8()解析后出现乱码。这个看似简单的编码问题背后,隐藏着…...

RANSAC算法:从理论到实战,解锁三维点云中的平面拟合

1. RANSAC算法:三维点云中的"找茬大师" 第一次接触三维点云数据时,我被那些密密麻麻的空间点震撼到了——就像在显微镜下看一群乱飞的萤火虫。但当导师让我从这些点里找出墙面和地面时,我彻底懵了。直到遇到RANSAC算法,…...

8051单片机sbit位操作失效问题与volatile解决方案

1. 问题现象与背景解析在8051单片机开发中,我们经常需要对寄存器或内存中的特定位进行操作。Keil C51编译器提供了sbit关键字来实现位寻址功能,这是一种非常高效的位操作方式。但在实际开发中,不少工程师遇到过这样的困扰:明明在代…...

C#从零开始学习笔记---第七天

不是同样的时间,不是同样的笔记,但是同样的作者。新的一天,欢迎收看我的学习笔记吼吼~我们昨天最后留了两道题,不知道大家做的怎么样,我现在来公布一下答案,但因为1000个人心里有1000个哈姆雷特&#xff0c…...

量子同态加密:理论与实践的突破

1. 量子同态加密:理论与实践的桥梁量子同态加密(Quantum Homomorphic Encryption, QHE)是密码学领域的一项突破性技术,它允许在加密的量子数据上直接执行任意量子计算,而无需事先解密。这项技术对于构建真正隐私保护的…...

一款支持USB2.0的4端口集线器芯片

GM8220C是成都振芯科技推出的一款支持USB2.0的4端口集线器芯片。它充分满足USB2.0和充电协议(BC1.1/1.2),具备多种工作模式和充电支持功能,适用于多种设备。1. 主要特征协议兼容:兼容USB2.0协议,并向下兼容…...

CanMV K230 家用电器电流识别 预告

数据采集:家用电器电流采集 数据分析:电流波形与特征 识别方法: 硬件设置: 算法部署: 电器可能包括:手机充电器、电脑、电视、热水壶等...

Perplexity引用格式设置全链路解析(含BibTeX/CSL/DOI自动映射底层逻辑)

更多请点击: https://kaifayun.com 第一章:Perplexity引用格式设置全链路解析(含BibTeX/CSL/DOI自动映射底层逻辑) Perplexity 在学术写作支持中并非原生集成引文管理,但其底层可对接外部文献元数据服务,实…...

ARM9老开发板救星:用BusyBox 1.7.0和4.3.2工具链构建根文件系统(避坑实录)

ARM9开发板重生指南:BusyBox 1.7.0与4.3.2工具链的黄金组合 当一块尘封多年的ARM9开发板重新出现在你面前,那种感觉就像考古学家发现了一件珍贵的文物。S3C2440这类老将虽然性能比不上现代Cortex-A系列,但在教学、工业控制等领域依然有不可替…...

A-59F所有应用模式说明

A-59F 是一款高集成语音处理模组,一体化实现 AI ENC 降噪、AEC 回音消除、扩音防啸叫、BF 波束拾音 四大核心能力。支持模拟 / 数字麦克风、模拟 / I2S 数字音频接口,邮票孔 SMT 封装,体积小巧、易嵌入,可大幅简化音频电路&#x…...

【网络安全】2026最新网安渗透测试标准及流程!新手小白零基础入门必看教程!

✅一、了解渗透测试 🔴什么是渗透测试? 渗透测试是一种安全性测试,通过发起模拟网络攻击的方式查找计算机系统中的漏洞。 渗透测试人员是拥有高超道德黑客技术的安全专业人员(道德黑客是指运用黑客工具和黑客技术来修复安全薄弱环…...

影刀RPA工程实战:多店铺环境隔离体系与自动化流程的事务性保障

一个店铺登录态串到另一个店铺,只在一瞬间。 但要真正杜绝它,需要的是一整套工程约束。 上一篇文章聊了浏览器实例池与并发调度,那套东西帮我们扛住了几十个店铺同时跑的稳定性。但很快我们又遇到了一个新问题:店铺之间的环境边界…...