Golang 接口(Interface)

一则简单的例子 type IGreeting interface { sayHello() } func sayHello(i IGreeting) { i.sayHello() } type Go struct {} func (g Go) sayHello() { fmt.Println("Hi, I am GO!") } type PHP struct {} func (p PHP) sayHello() { fmt.Println("Hi, I am PHP!") } func main() { golang := Go{} php := PHP{} sayHello(golang) sayHello(php) } 如何通过接口实现多态 多态的字面意思是“多种形态”。在编程中,它指的是: 同一操作作用于不同的对象,可以有不同的解释,产生不同的执行结果。 通过多态,程序可以在运行时根...

二月 6, 2025 · 7 分钟 · 3443 字 · ZhangYong

PHP的内存回收机制

本篇文章介绍PHP的内存回收机制,帮助我们理解在函数执行结束后,其作用域下的变量是如何释放其内存空间的。 「引用计数」和「Garbage Collector」是内存回收的主要机制,「内存池」部分介绍“回收”这个动作代表的更底层的Zend Engine实现细节。 引用计数 PHP变量的基本单...

一月 18, 2025 · 7 分钟 · 3064 字 · ZhangYong

PHP的反射机制

PHP的反射机制是一种强大的工具,它允许程序在运行时检查和操作类、对象、接口、方法、属性等元素。通过反射,你可以动态地创建对象、调用方法、访问属性,甚至可以改变类的行为。 https://www.php.net/manual/zh/book.reflection.php 基本反射类 ReflectionClass:用于获取类的信息,可以实例化一个类并调用其方法。 Reflectio...

一月 6, 2025 · 3 分钟 · 1347 字 · ZhangYong

Golang 底层实现之map

Map的实现原理 golang 的 map 底层是哈希表查找,平均查找效率是 O(1),最差是 O(N) go源码 在源码中,表示 map 的结构体是 hmap,它是 hashmap 的“缩写”: // A header for a Go map. type hmap struct { count int // 元素个数,调用 len(map) 时,直接返回此值 flags uint8 B uint8 // buckets 的对数 log_2 noverflow uint16 // overflow 的 bucket 近似数,做扩容决策II的判断 hash0 uint32 // hash seed buckets unsafe.Pointer // 指向 buckets 数组...

十二月 20, 2024 · 14 分钟 · 6600 字 · ZhangYong

PHP 底层实现之数组

曾经听前同事讲过一句话「PHP的精髓是他的数组」。 彼时年龄和经验都尚浅,对这句话体会不是很深。但自从开始写golang,我是越来越怀念PHP数组那种简单、粗暴的,不管三七二十一,拿来直接往里面塞的编码体验了。 于是,便有了这篇探索PHP到底是如何实现这个能够「容纳万物」的数据类型的...

十一月 15, 2024 · 10 分钟 · 4709 字 · ZhangYong

计算机系统之CPU

CPU 从晶体管到运算器 简单晶体管 -> AND/OR/NOT门 -> 加法(与或非门)-> 运算器(arithmetic/logic unit,ALU) 寄存器 简单晶体管 -> NAND门(与非门)-> 存储1bit位 -> 寄存器 指令集 CPU运算器的菜谱,最底层也是最基础的计算机语言。 这条指令占据16...

八月 29, 2024 · 2 分钟 · 761 字 · ZhangYong

Golang Redis分布式锁实现

package lock import ( "context" "errors" "cache" "time" "github.com/go-redis/redis/v8" "github.com/google/uuid" ) const ( DefaultExpirationTime = 5 * time.Second RenewInterval = DefaultExpirationTime / 2 // 续租间隔为锁过期时间的一半 LuaCheckAndDelKey = ` if(redis.call('get',KEYS[1])==ARGV[1]) then return redis.call('del',KEYS[1]) else return 0 end ` LuaCheckAndRenewKey = ` if(redis.call('get',KEYS[1])==ARGV[1]) then return redis.call('expire',KEYS[1],ARGV[2]) else return 0 end ` ) type RedisLock struct { key string val string expiration time.Duration cli *redis.Client script *redis.Script // 用于解锁的 Lua 脚本 renewScript *redis.Script // 用于续租的 Lua 脚本 stopChan chan struct{} // 用于停止续租 goroutine } func NewRedisLock(key string) *RedisLock { val := uuid.New().String() return &RedisLock{ key: key, val: val, expiration: DefaultExpirationTime, cli: cache.RedisV8Client, script: redis.NewScript(LuaCheckAndDelKey), renewScript: redis.NewScript(LuaCheckAndRenewKey), stopChan: make(chan struct{}), } } func (r *RedisLock) Lock(ctx context.Context)...

八月 14, 2024 · 1 分钟 · 329 字 · ZhangYong

加密哈希、非加密哈希和一致性哈希

哈希函数 哈希函数又称散列算法,是一种从任何一种数据中创建小的数字“指纹”的方法。散列函数把消息或数据压缩成摘要,使得数据量变小,将数据的格式固定下来。该函数将数据打乱混合,重新创建一个叫做散列值(又叫哈希值)(hash values,hash codes,hash sums,或hash...

七月 4, 2024 · 5 分钟 · 2040 字 · ZhangYong

脚本拉取pprof数据分析服务cpu偶发突刺问题

最近工作中遇到一个比较奇怪的问题,容器化部署的服务container会在不定时偶发CPU突刺,从而引发频繁动态扩容。 服务是go开发的,所以准备让服务提供pprof接口来分析CPU的使用情况。 但由于CPU突刺是不定时的,并且网关一般都有请求读写超时配置。 所以我们不能一次拉取太长时间...

六月 19, 2024 · 2 分钟 · 753 字 · ZhangYong

ChatGPT Prompt Summary of Skills

First Of All This is important which the official docs is later and more detailed than summary ⬇️⬇️⬇️️ https://platform.openai.com/docs/examples To do & Not to do Instead of just saying what not to do, say what to do instead. 与其告知模型不能干什么,不妨告诉模型能干什么。 场景 Less Effective Better 原因 推荐雅思必背英文单词 Please suggest me some essential words for IELTS Please suggest me 10 essential words for IELTS 后者 prompt 会更加明确,前者会给大概 20 个单词。这个仍然有提升的空间,比如增加更多的限定...

六月 13, 2024 · 4 分钟 · 1813 字 · ZhangYong