Deprecated: parse_url(): Passing null to parameter #1 ($url) of type string is deprecated in /www/wwwroot/blog_qqvbc_com/usr/plugins/Access/Access_Core.php on line 339

Deprecated: parse_url(): Passing null to parameter #1 ($url) of type string is deprecated in /www/wwwroot/blog_qqvbc_com/usr/plugins/Access/Access_Core.php on line 392

Deprecated: parse_url(): Passing null to parameter #1 ($url) of type string is deprecated in /www/wwwroot/blog_qqvbc_com/usr/plugins/Access/Access_Core.php on line 394
Joyber 的博客

Redis Lua原子操作 + 电商秒杀超卖超卖完整解决方案

说明:全文极简、重实战、无废话,包含 Redis Lua基础用法 + 原子特性原理 + 高并发秒杀防超卖完整落地方案,可直接用于生产环境。

一、Redis Lua 核心知识点(必懂)

1. 为什么Redis需要Lua脚本

作用:将多条Redis命令打包为单个原子指令执行

  • 普通多条命令:存在并发时差、线程安全问题
  • Lua脚本:执行不插针、不中断、原子串行
  • 解决:并发竞争、超卖、库存错乱、分布式锁竞争问题

2. Redis Lua 执行特性(硬核规则)

  • 单个Lua脚本:要么全部执行成功,要么全部失败
  • 脚本执行期间,其他客户端命令全部阻塞等待
  • 不支持事务回滚,但天然具备事务原子性
  • 性能极高:一次网络IO完成多条命令,减少网络开销

3. Redis Lua 标准语法模板

作用:固定传参、取值、返回格式,生产统一规范

-- KEYS[1]、KEYS[2] 传入key
-- ARGV[1]、ARGV[2] 传入参数值
return redis.call("命令名", KEYS[1], ARGV[1])

4. 常用Redis Lua命令

-- 取值
redis.call("GET", KEYS[1])
-- 设值
redis.call("SET", KEYS[1], ARGV[1])
-- 自增/自减
redis.call("INCR", KEYS[1])
redis.call("DECR", KEYS[1])
-- 判断存在
redis.call("EXISTS", KEYS[1])

5. Java/Python 调用Redis Lua通用格式

Python示例

import redis

r = redis.Redis(decode_responses=True)

# 加载Lua脚本
lua_script = """
return redis.call('GET', KEYS[1])
"""

# 执行脚本:keys列表、args列表
res = r.eval(lua_script, 1, "goods_stock")
print(res)

二、秒杀超卖问题根源

场景:库存10件,1000人同时抢购

普通代码bug流程

  1. 线程A查询库存 = 10
  2. 线程B查询库存 = 10(未扣减,并发同时读到充足库存)
  3. 线程A、B同时扣减 → 库存变为8,卖出12件,超卖

本质原因查库存、判库存、扣库存 非原子操作

三、Lua原子防超卖核心思路

一条Lua脚本完成三件原子操作(不可分割)

  1. 查询当前商品库存
  2. 判断库存是否大于0
  3. 满足则扣减库存,不满足直接返回失败

全程单线程执行,杜绝并发同时判定通过

四、完整可上线:秒杀防超卖Lua脚本

1. 脚本功能说明

  • 支持单商品限购1件(防止单人多抢)
  • 原子判定库存 + 原子扣减
  • 记录已抢购用户,防止重复下单
  • 返回状态码,前端/后端可直接判断结果

2. 最终生产级Lua脚本

-- KEYS[1]:商品库存key
-- KEYS[2]:用户抢购记录key
-- ARGV[1]:用户ID
-- ARGV[2]:本次抢购数量(固定1)

-- 1. 判断用户是否已抢购过(防重复下单)
local has_buy = redis.call("sismember", KEYS[2], ARGV[1])
if has_buy == 1 then
    return 0  -- 0:重复抢购,失败
end

-- 2. 获取当前库存
local stock = tonumber(redis.call("get", KEYS[1]) or 0)

-- 3. 库存不足直接返回
if stock < 1 then
    return -1 -- -1:库存不足,秒杀结束
end

-- 4. 原子扣减库存
redis.call("decr", KEYS[1])

-- 5. 记录用户抢购记录
redis.call("sadd", KEYS[2], ARGV[1])

-- 6. 秒杀成功
return 1

3. 返回码统一规范

  • 1:秒杀成功
  • 0:用户重复抢购
  • -1:库存不足、超卖拦截

五、高并发秒杀完整业务流程(无漏洞)

1. 秒杀预热(提前初始化库存)

# 初始化商品库存100件
SET seckill:goods:1001:stock 100
# 用户抢购记录集合
SADD seckill:goods:1001:user

2. 完整执行链路(层层拦截,抗百万并发)

前端拦截:按钮置灰、防抖、倒计时

网关拦截:限流、防刷、IP限制

Redis Lua原子拦截:防超卖、防重复抢(核心)

异步落库:秒杀成功后,MQ异步写入数据库(扛高并发)

六、Python 完整可运行秒杀Demo

功能:模拟100并发抢10库存,绝对无超卖

import redis
import threading

# 连接Redis
r = redis.Redis(decode_responses=True)

# 秒杀Lua脚本
SECKILL_LUA = """
local has_buy = redis.call("sismember", KEYS[2], ARGV[1])
if has_buy == 1 then
    return 0
end

local stock = tonumber(redis.call("get", KEYS[1]) or 0)
if stock < 1 then
    return -1
end

redis.call("decr", KEYS[1])
redis.call("sadd", KEYS[2], ARGV[1])
return 1
"""

# 初始化库存10
r.set("seckill:stock", 10)

def seckill(user_id):
    """单个用户抢购"""
    res = r.eval(SECKILL_LUA, 2, "seckill:stock", "seckill:user", user_id)
    if res == 1:
        print(f"用户{user_id} 秒杀成功")
    elif res == 0:
        print(f"用户{user_id} 重复抢购")
    else:
        print(f"用户{user_id} 秒杀失败,库存不足")

# 模拟100个并发线程
if __name__ == "__main__":
    thread_list = []
    for i in range(1,101):
        t = threading.Thread(target=seckill, args=(f"user{i}",))
        thread_list.append(t)
        t.start()

    for t in thread_list:
        t.join()

    # 最终库存校验
    final_stock = r.get("seckill:stock")
    print("最终剩余库存:", final_stock)
    print("成功抢购人数:", r.scard("seckill:user"))

七、PHP 完整可运行秒杀Demo(生产可用+高并发模拟)

功能:基于PHP Redis扩展 + Lua原子脚本,模拟高并发秒杀,彻底防超卖、防重复抢购,适配PHP框架(ThinkPHP/Laravel)原生使用

环境要求:安装PHP Redis扩展 pecl install redis

<?php
// 环境要求:安装PHP Redis扩展、开启pcntl多进程扩展(模拟高并发)
// 生产适配:兼容Laravel/ThinkPHP/Swoole所有PHP项目

// 1. 连接Redis
$redis = new Redis();
$redis->connect('127.0.0.1', 6379);
// 解决Redis超时、并发连接问题
$redis->setOption(Redis::OPT_READ_TIMEOUT, -1);

// 2. 生产级秒杀Lua脚本(原子防超卖、防重复抢购)
$luaScript = <<<LUA
local has_buy = redis.call("sismember", KEYS[2], ARGV[1])
if has_buy == 1 then
    return 0
end

local stock = tonumber(redis.call("get", KEYS[1]) or 0)
if stock < 1 then
    return -1
end

redis.call("decr", KEYS[1])
redis.call("sadd", KEYS[2], ARGV[1])
return 1
LUA;

// 3. 初始化秒杀库存(仅首次执行,可后台预热执行)
$redis->del('seckill:stock');
$redis->del('seckill:user');
$redis->set('seckill:stock', 10);

/**
 * 秒杀核心原子方法
 * @param string $userId 唯一用户ID
 * @return int 1=成功 0=重复抢购 -1=库存不足
 */
function seckill(string $userId): int
{
    global $redis, $luaScript;
    // PHP eval固定参数:脚本内容、[KEYS+ARGV数组]、KEYS参数数量
    return $redis->eval($luaScript, [
        'seckill:stock',
        'seckill:user',
        $userId
    ], 2);
}

/**
 * 多进程模拟高并发秒杀(100用户并发抢10库存)
 */
function batchSeckill()
{
    $processNum = 100;
    for ($i = 1; $i <= $processNum; $i++) {
        $pid = pcntl_fork();
        if ($pid == 0) {
            // 子进程执行秒杀
            $userId = 'user_' . $i;
            $res = seckill($userId);
            switch ($res) {
                case 1:
                    echo "【成功】{$userId} 秒杀下单完成\n";
                    break;
                case 0:
                    echo "【拦截】{$userId} 禁止重复抢购\n";
                    break;
                case -1:
                    echo "【售罄】{$userId} 库存不足,秒杀失败\n";
                    break;
            }
            // 必须退出子进程,避免循环派生
            exit(0);
        }
    }

    // 等待所有子进程执行完毕
    while (pcntl_waitpid(0, $status) != -1);
}

// 执行高并发秒杀模拟
batchSeckill();

// 4. 最终数据校验(杜绝超卖核心校验)
global $redis;
$finalStock = $redis->get('seckill:stock');
$successNum = $redis->sCard('seckill:user');

echo "\n========== 秒杀最终统计结果 ==========\n";
echo "剩余库存数量:{$finalStock}\n";
echo "成功下单人数:{$successNum}\n";
echo "校验结果:" . ($finalStock + $successNum == 10 ? "✅ 无超卖、无漏卖,数据正常" : "❌ 数据异常") . "\n";

$redis->close();
?>

一、PHP版本核心特性说明

  • 原子性互通:Lua脚本与Python版本完全一致,底层原子锁库存逻辑通用,跨语言无差异
  • PHP独有规则:Redis eval方法参数顺序固定,必须严格区分KEYS数量,否则脚本执行报错
  • 框架无缝适配:可直接移植 Laravel/ThinkPHP/Swoole 项目,仅需替换框架Redis实例
  • 高并发适配性:基于多进程模拟真实秒杀流量,兼容PHP-FPM、Swoole协程环境,分布式集群完全生效
  • 数据强一致性:最终库存+成功人数恒等于初始库存,彻底杜绝超卖、少卖、漏卖问题

二、PHP生产部署注意事项

  • 线上关闭pcntl多进程代码,仅用业务接口接收请求,多进程仅用于本地压测验证
  • Lua脚本建议使用script load预加载缓存,通过sha1值调用,减少网络传输开销
  • 秒杀Redis Key设置过期时间,自动清理过期秒杀数据,避免内存堆积
  • 接口层增加限流、防刷、IP黑白名单,拦截恶意黄牛请求
  • 脚本预加载优化:生产环境禁止每次请求传递完整Lua脚本,采用script\_load预加载+sha1哈希调用,大幅减少网络IO、提升并发吞吐量

三、PHP Lua脚本缓存(SHA1)生产优化代码

优化作用:首次加载脚本生成唯一SHA1哈希值,后续所有秒杀请求直接通过哈希值调用脚本,无需重复传输大段脚本内容,高并发场景性能提升30%+

<?php
// 连接Redis
$redis = new Redis();
$redis->connect('127.0.0.1', 6379);
$redis->setOption(Redis::OPT_READ_TIMEOUT, -1);

// 秒杀Lua脚本
$luaScript = <<<LUA
local has_buy = redis.call("sismember", KEYS[2], ARGV[1])
if has_buy == 1 then
    return 0
end
local stock = tonumber(redis.call("get", KEYS[1]) or 0)
if stock < 1 then
    return -1
end
redis.call("decr", KEYS[1])
redis.call("sadd", KEYS[2], ARGV[1])
return 1
LUA;

// 核心:预加载脚本,获取SHA1哈希值(项目初始化执行一次即可)
$sha1Hash = $redis->script('load', $luaScript);
echo "脚本缓存SHA1值:" . $sha1Hash . "\n";

/**
 * 缓存版秒杀方法(生产正式使用)
 * 无需传递完整脚本,仅通过SHA1调用,性能更高
 */
function fastSeckill(string $userId, string $sha1Hash): int
{
    global $redis;
    // evalsha 哈希调用脚本
    return $redis->evalsha($sha1Hash, [
        'seckill:stock',
        'seckill:user',
        $userId
    ], 2);
}

// 初始化库存
$redis->del('seckill:stock', 'seckill:user');
$redis->set('seckill:stock', 10);

// 测试缓存版秒杀
$res = fastSeckill('user_001', $sha1Hash);
var_dump($res);

// 脚本状态校验(判断脚本是否已缓存)
$isExists = $redis->script('exists', $sha1Hash);
echo "脚本是否缓存成功:" . ($isExists[0] ? "是" : "否") . "\n";

$redis->close();
?>

四、脚本缓存生产高可用方案(自动降级容错)

核心解决问题:Redis重启、缓存脚本丢失、evalsha执行失败等线上突发异常,无感知自动降级,保障秒杀服务不宕机、不报错

<?php
// 连接Redis
$redis = new Redis();
$redis->connect('127.0.0.1', 6379);
$redis->setOption(Redis::OPT_READ_TIMEOUT, -1);

// 原始秒杀Lua脚本
$luaScript = <<<LUA
local has_buy = redis.call("sismember", KEYS[2], ARGV[1])
if has_buy == 1 then
    return 0
end
local stock = tonumber(redis.call("get", KEYS[1]) or 0)
if stock < 1 then
    return -1
end
redis.call("decr", KEYS[1])
redis.call("sadd", KEYS[2], ARGV[1])
return 1
LUA;

// 项目初始化预加载脚本,全局缓存SHA1值
$sha1Hash = $redis->script('load', $luaScript);

/**
 * 高可用秒杀方法(缓存优先 + 自动降级)
 * 优先evalsha高性能调用,失败自动降级eval原生调用
 * @param string $userId 用户唯一ID
 * @return int 1成功 0重复 -1库存不足
 */
function safeSeckill(string $userId): int
{
    global $redis, $sha1Hash, $luaScript;

    $keys = ['seckill:stock', 'seckill:user', $userId];
    $keyNum = 2;

    try {
        // 优先使用缓存脚本(高性能)
        return $redis->evalsha($sha1Hash, $keys, $keyNum);
    } catch (RedisException $e) {
        // 捕获脚本不存在异常,自动降级原生执行
        if (str_contains($e->getMessage(), 'NOSCRIPT')) {
            // 重新加载脚本缓存,修复异常
            $GLOBALS['sha1Hash'] = $redis->script('load', $luaScript);
            // 降级执行完整脚本
            return $redis->eval($luaScript, $keys, $keyNum);
        }
        // 其他异常直接抛出
        throw $e;
    }
}

// 初始化秒杀库存
$redis->del('seckill:stock', 'seckill:user');
$redis->set('seckill:stock', 10);

// 模拟多次秒杀调用,验证容错性
for ($i = 1; $i <= 5; $i++) {
    $res = safeSeckill('user_' . $i);
    echo "用户user_{$i} 结果:" . ($res === 1 ? "秒杀成功" : "失败") . "\n";
}

// 最终数据校验
$finalStock = $redis->get('seckill:stock');
$successNum = $redis->sCard('seckill:user');
echo "\n========== 高可用秒杀结果 ==========\n";
echo "剩余库存:{$finalStock}\n";
echo "成功人数:{$successNum}\n";

$redis->close();
?>

五、高可用方案核心特性

  • 智能优先策略:正常场景使用 evalsha 缓存调用,性能拉满
  • 无感自动降级:捕捉 NOSCRIPT 脚本丢失异常,自动重新加载脚本并降级原生执行
  • 自愈修复能力:异常后自动更新全局SHA1缓存,后续请求恢复高性能模式
  • 业务零影响:整个容错过程无报错、无中断,用户完全感知不到

六、脚本缓存生产使用规范

  • 加载时机:项目启动、框架初始化时执行一次 script load,常驻Redis缓存,无需重复加载
  • 缓存有效期:Redis不主动清理缓存脚本,重启Redis后依赖自动降级逻辑自愈
  • 统一复用:全局统一SHA1常量,所有秒杀接口共用缓存脚本,避免重复加载
  • 异常监控:线上可捕获降级日志,用于监控Redis脚本缓存异常频次,及时排查问题
  • 加载时机:项目启动、框架初始化时执行一次 script load,常驻Redis缓存,无需重复加载
  • 缓存有效期:Redis不主动清理缓存脚本,重启Redis后需重新加载
  • 降级方案:若evalsha报错(脚本丢失),自动降级为eval完整脚本加载,保障服务不中断
  • 统一复用:全局统一SHA1常量,所有秒杀接口共用缓存脚本,避免重复加载

八、彻底解决超卖超买的核心原理总结

1. 为什么普通代码会超卖

查库存、判库存、扣库存 三步非原子,并发间隙导致多人同时抢到资格

2. 为什么Lua能彻底杜绝超卖

Redis单线程执行Lua脚本,整个秒杀逻辑串行原子执行,无间隙、无并发穿插,从底层锁死库存竞争

九、生产环境额外优化(高阶)

  • 脚本缓存:使用 script load + sha1 缓存脚本,不用每次传完整脚本
  • 过期时间:秒杀key设置过期时间,自动释放内存
  • 限流熔断:接口层增加QPS限流,避免打垮Redis
  • 异步落库:Redis只做预扣减,MQ异步更新MySQL,提升吞吐量
  • 防黄牛:绑定用户、IP、设备号,限制单用户限购次数

十、常见误区避坑

  • 误区:Java加锁(synchronized/lock)防超卖

问题:分布式集群部署,单机锁完全失效

  • 误区:Redis多条普通命令判库存

问题:命令之间存在并发空隙,必然超卖

  • 唯一稳妥方案Redis Lua原子脚本(行业通用秒杀最终方案)

Python 进阶极简教程(高阶核心+纯用法)

python基础版

说明:承接Python基础教程,全文无冗余描述,仅保留进阶核心知识点 + 作用 + 可运行代码,覆盖Python后端、脚本、工程化全部高阶刚需内容。

一、变量与深浅拷贝(进阶核心)

1. 引用机制原理

作用:弄懂赋值、浅拷贝、深拷贝区别,解决数据篡改问题

# 赋值:只是绑定同一内存地址(完全共享数据)
a = [1, 2, [3, 4]]
b = a
b[0] = 99
print(a) # a同步被修改

2. 浅拷贝 copy

作用:拷贝一层数据,内层嵌套对象依旧引用

import copy
a = [1, 2, [3, 4]]
b = copy.copy(a)
b[0] = 99       # 外层独立,不影响原数据
b[2][0] = 999   # 内层嵌套共享,原数据被修改
print(a)

3. 深拷贝 deepcopy

作用:递归拷贝所有层级,完全独立数据,互不影响

import copy
a = [1, 2, [3, 4]]
b = copy.deepcopy(a)
b[2][0] = 999
print(a) # 原数据完全不变

二、函数高阶特性

1. 闭包

作用:内层函数捕获外层局部变量,保存私有状态,数据常驻内存

def counter():
    num = 0
    def inner():
        nonlocal num # 声明使用外层变量
        num += 1
        return num
    return inner

# 多个实例状态独立
c1 = counter()
c2 = counter()
print(c1()) # 1
print(c1()) # 2
print(c2()) # 1

2. 装饰器(无参/有参)

作用:不修改原函数代码,动态扩展功能(日志、校验、计时)

# 无参装饰器
def wrapper(func):
    def inner(*args, **kwargs):
        print("执行前")
        res = func(*args, **kwargs)
        print("执行后")
        return res
    return inner

@wrapper
def test():
    print("核心逻辑")

test()

3. 递归优化与尾递归

作用:简化循环逻辑,处理层级嵌套数据

# 阶乘递归
def fact(n):
    if n == 1:
        return 1
    return n * fact(n-1)

print(fact(10))

4. 函数缓存 lru\_cache

作用:缓存函数返回值,解决递归重复计算,大幅提速

from functools import lru_cache

@lru_cache(maxsize=None)
def fib(n):
    if n <= 2:
        return 1
    return fib(n-1) + fib(n-2)

print(fib(30))

三、高阶语法与推导式

1. 四大推导式

作用:极简代码快速生成容器数据,开发高频用法

# 列表推导式
lst = [x for x in range(10) if x % 2 == 0]

# 字典推导式
dic = {k:v for k,v in zip(["a","b"], [1,2])}

# 集合推导式
s = {x**2 for x in [1,2,2,3]}

# 生成器推导式(省内存)
gen = (x for x in range(10))
print(next(gen))

2. 高阶函数 map/filter/reduce

作用:批量处理、过滤、聚合数据

from functools import reduce
lst = [1,2,3,4]

# map 批量处理
res1 = list(map(lambda x:x*2, lst))

# filter 过滤数据
res2 = list(filter(lambda x:x>2, lst))

# reduce 累计聚合
res3 = reduce(lambda a,b:a+b, lst)

print(res1, res2, res3)

四、面向对象进阶

1. 类属性与实例属性

作用:区分全局类属性、私有实例属性,优化内存

class Demo:
    cls_val = 100 # 类属性(全局共享)
    def __init__(self, val):
        self.val = val # 实例属性(独立私有)

d1 = Demo(200)
d2 = Demo(300)
print(Demo.cls_val)
print(d1.val, d2.val)

2. 三大方法(实例/类/静态)

作用:适配不同场景的类调用逻辑

class Test:
    # 实例方法:必须实例调用,自带self
    def func1(self):
        pass

    # 类方法:类/实例均可调用,自带cls
    @classmethod
    def func2(cls):
        pass

    # 静态方法:无默认参数,纯工具方法
    @staticmethod
    def func3():
        pass

3. 继承、重写、多继承

作用:代码复用,实现多态特性

# 父类
class Father:
    def show(self):
        print("父类方法")

# 子类继承 + 方法重写
class Son(Father):
    def show(self):
        print("子类重写方法")

s = Son()
s.show()

4. 私有属性与属性装饰器

作用:数据封装,控制属性读写权限

class User:
    def __init__(self, age):
        self.__age = age # 私有属性(外部无法直接访问)

    # 属性装饰器:将方法转为属性调用
    @property
    def age(self):
        return self.__age

u = User(18)
print(u.age)

五、迭代器与生成器(性能优化)

1. 迭代器原理

作用:统一遍历规则,节省内存

lst = [1,2,3]
it = iter(lst) # 获取迭代器
print(next(it))
print(next(it))

2. 生成器 yield

作用:边执行边返回,不一次性加载所有数据,处理超大数据集

def gen():
    yield 1
    yield 2
    yield 3

g = gen()
print(next(g))
print(next(g))

# 遍历生成器
for i in gen():
    print(i)

六、异常处理进阶

1. 完整异常捕获结构

作用:精准捕获异常,程序不崩溃

try:
    num = 1 / 0
except ZeroDivisionError as e:
    print("除零错误:", e)
except Exception as e:
    print("通用错误:", e)
else:
    print("无异常执行")
finally:
    print("必定执行")

2. 主动抛异常

作用:参数校验、逻辑拦截主动终止程序

def check_age(age):
    if age < 0:
        raise ValueError("年龄不能为负数")

check_age(-1)

七、文件与上下文管理器

1. with 上下文管理器

作用:自动关闭文件、释放资源,无需手动close

# 读写文件自动释放
with open("test.txt", "w", encoding="utf-8") as f:
    f.write("进阶测试")

with open("test.txt", "r", encoding="utf-8") as f:
    print(f.read())

2. 自定义上下文管理器

作用:自定义资源开启、关闭逻辑

class MyCtx:
    def __enter__(self):
        print("开启资源")
        return self
    def __exit__(self, exc_type, exc_val, exc_tb):
        print("关闭资源")

with MyCtx():
    print("执行业务逻辑")

八、模块、包与导包进阶

1. \_\_init\_\_.py 作用

作用:标识文件夹为Python包,统一导出接口

# 在包目录 __init__.py 中定义
__all__ = ["func1", "Demo"] # 控制from xxx import * 导入内容

# 批量导出
from .test import func1, Demo

2. 动态导包

作用:程序运行中动态导入模块,灵活解耦

import importlib

# 动态导入指定模块
module = importlib.import_module("math")
print(module.pi)

九、多线程与多进程

1. 多线程(IO密集型)

作用:处理等待、文件、网络IO任务

import threading
import time

def task(name):
    print(f"线程{name}执行")
    time.sleep(1)

t = threading.Thread(target=task, args=("A",))
t.start()
t.join() # 等待线程结束

2. 多进程(CPU密集型)

作用:绕过GIL全局锁,多核并行计算

from multiprocessing import Process

def task():
    print("子进程执行")

if __name__ == "__main__":
    p = Process(target=task)
    p.start()
    p.join()

十、协程异步编程

作用:超高并发IO处理,性能远超多线程

import asyncio

# 异步函数
async def async_task(num):
    print(f"任务{num}开始")
    await asyncio.sleep(1)
    print(f"任务{num}结束")

# 并发执行
async def main():
    tasks = [async_task(1), async_task(2)]
    await asyncio.gather(*tasks)

asyncio.run(main())

十一、正则表达式进阶

作用:复杂文本匹配、提取、替换、校验

import re

s = "Python123Java456"

# 匹配所有数字
res1 = re.findall(r"\d+", s)
# 匹配所有字母
res2 = re.findall(r"\a+", s)
# 替换指定内容
res3 = re.sub(r"\d", "", s)

print(res1, res2, res3)

十二、GIL锁与性能优化

作用:理解Python单线程特性,针对性优化代码

  • GIL全局解释器锁:同一时刻一个进程只有一个线程执行Python代码
  • CPU密集:用多进程规避GIL
  • IO密集:用多线程/协程提升效率

十三、常用工程化技巧

1. 枚举类

作用:固定常量状态,避免魔法值

from enum import Enum

class Status(Enum):
    SUCCESS = 200
    FAIL = 500

print(Status.SUCCESS.value)

2. 时间处理

作用:时间戳、格式化、时间差计算

from datetime import datetime

# 当前时间
now = datetime.now()
# 格式化时间
time_str = now.strftime("%Y-%m-%d %H:%M:%S")
print(time_str)

Lua 进阶极简教程(高阶核心+纯用法)

lua基础版

说明:承接Lua基础教程,全文无冗余描述,仅保留进阶核心知识点 + 作用 + 可运行代码,覆盖Lua高阶开发全部刚需内容。

一、变量深层特性(进阶必懂)

1. 全局环境 \_G

作用:存储所有全局变量、函数的全局表,可动态遍历、修改全局内容

-- 查看所有全局变量
print(_G)

-- 定义全局变量等价写法
_G.testVal = 100
print(testVal)

-- 遍历所有全局函数/变量
for k,v in pairs(_G) do
    print(k,v)
end

2. 局部变量优化

作用:局部变量访问速度远快于全局变量,高阶开发优先局部缓存

-- 缓存全局函数,提升执行效率
local print = print
local pairs = pairs

print("优化后的局部调用")

3. 变量nil清空与垃圾回收

作用:主动置空变量,触发GC释放内存,避免内存泄漏

local data = {1,2,3,4}
data = nil -- 置空引用,等待GC回收
collectgarbage() -- 手动触发垃圾回收

二、函数进阶(Lua核心高阶)

1. 闭包(Closure)

作用:内层函数捕获外层局部变量,变量常驻内存,实现数据私有、状态保存

local function counter()
    local num = 0 -- 被捕获的局部变量
    return function()
        num = num + 1
        return num
    end
end

-- 独立状态,互不干扰
local c1 = counter()
local c2 = counter()
print(c1()) -- 1
print(c1()) -- 2
print(c2()) -- 1

2. 函数尾调用(Tail Call)

作用:尾部调用函数,不堆叠栈帧,避免递归栈溢出,优化递归性能

-- 尾递归写法(无栈溢出)
local function factorial(n, res)
    res = res or 1
    if n <= 1 then return res end
    return factorial(n-1, n*res) -- 纯粹尾部返回
end

print(factorial(10))

3. 函数重载模拟

作用:Lua无原生重载,通过判断参数数量/类型实现多参数适配

local function add(...)
    local args = {...}
    if #args == 1 then
        return args[1] * 2
    elseif #args == 2 then
        return args[1] + args[2]
    end
end

print(add(10))  -- 20
print(add(10,20)) -- 30

4. 函数缓存(记忆化)

作用:缓存函数执行结果,避免重复计算,大幅提升高频函数效率

local cache = {}
local function fib(n)
    if cache[n] then return cache[n] end
    if n <= 2 then return 1 end
    local res = fib(n-1) + fib(n-2)
    cache[n] = res
    return res
end

print(fib(30))

三、Table 高阶操作(Lua灵魂)

1. 数组与哈希表分离原理

作用:Lua table 内部分数组段(连续数字key)、哈希段(自定义key),优化存储

-- 纯数组(高效)
local arr = {1,2,3,4}
-- 纯哈希(高效)
local hash = {a=1,b=2}
-- 混合表(性能略低,不推荐高频使用)
local mix = {1,2,a=3,b=4}

2. 表深拷贝/浅拷贝

作用:解决table默认引用赋值问题,独立复制数据表

-- 浅拷贝(仅复制一层)
local function shallowCopy(t)
    local res = {}
    for k,v in pairs(t) do res[k] = v end
    return res
end

-- 深拷贝(递归复制所有层级)
local function deepCopy(t)
    local res = {}
    if type(t) ~= "table" then return t end
    for k,v in pairs(t) do
        res[k] = deepCopy(v)
    end
    return res
end

local t1 = {1,2,{3,4}}
local t2 = deepCopy(t1)
t2[3][1] = 99
print(t1[3][1]) -- 原表不变

3. 表去重/排序/过滤

作用:高频数组处理工具方法

-- 数组去重
local function unique(arr)
    local temp = {}
    local res = {}
    for _,v in ipairs(arr) do
        if not temp[v] then
            temp[v] = true
            table.insert(res, v)
        end
    end
    return res
end

-- 自定义排序
local arr = {3,1,4,2}
table.sort(arr, function(a,b)
    return a > b -- 降序,默认升序
end)
print(table.concat(arr, ","))

四、元表与元方法(Lua进阶核心)

1. 基础元表读写

作用:为table绑定元表,拦截、自定义table操作行为

local t = {}
local mt = {}

setmetatable(t, mt) -- 绑定元表
local getMt = getmetatable(t) -- 获取元表
print(getMt == mt)

2. 常用元方法全覆盖

作用:拦截加减乘除、取值、赋值、长度、打印等操作

local t = {10,20}
local mt = {
    -- 取值拦截:t[key]
    __index = function(tab, k)
        return "默认值"
    end,
    -- 赋值拦截:t[key] = v
    __newindex = function(tab, k, v)
        print("禁止赋值")
    end,
    -- 加法重载 t1 + t2
    __add = function(a,b)
        return {a[1]+b[1], a[2]+b[2]}
    end,
    -- 打印重载 print(t)
    __tostring = function(tab)
        return "自定义表字符串"
    end,
    -- 长度重载 #t
    __len = function()
        return 99
    end
}

setmetatable(t, mt)
print(t[3])
t[1] = 999
print(t)
print(#t)

3. \_\_index 索引优化(继承核心)

作用:实现表的默认值、数据继承、查找降级

-- 默认值配置
local default = {name="默认", age=18}
local t = {}
setmetatable(t, {__index = default})

print(t.name) -- 找不到key,去元表查找

五、面向对象高阶(纯Lua实现)

1. 标准类、继承、重写

作用:完整OOP体系,支持封装、单继承、方法重写

-- 父类
local Person = {}
Person.__index = Person

function Person:new(name, age)
    local self = setmetatable({}, Person)
    self.name = name
    self.age = age
    return self
end

function Person:show()
    print(self.name, self.age)
end

-- 子类继承
local Student = {}
Student.__index = Student
setmetatable(Student, Person) -- 继承父类

function Student:new(name, age, id)
    local self = Person:new(name, age)
    self.id = id
    return setmetatable(self, Student)
end

-- 方法重写
function Student:show()
    print("学生:", self.name, self.id)
end

local s = Student:new("张三", 16, "001")
s:show()

2. 私有变量模拟

作用:通过闭包实现类私有属性,外部无法修改

local function User(name)
    -- 私有变量
    local _name = name

    -- 公开方法
    return {
        getName = function()
            return _name
        end,
        setName = function(n)
            _name = n
        end
    }
end

local u = User("李四")
print(u.getName())
-- print(u._name) 无法访问私有变量

六、协程高阶(Lua特色)

1. 协程完整生命周期

作用:掌握协程创建、启动、暂停、恢复、状态判断

local co = coroutine.create(function()
    print("协程第一步")
    coroutine.yield("暂停返回值")
    print("协程第二步")
    return "结束返回值"
end)

print(coroutine.status(co)) -- suspended 挂起
local ok, res1 = coroutine.resume(co)
print(res1)
local ok2, res2 = coroutine.resume(co)
print(res2)
print(coroutine.status(co)) -- dead 结束

2. 协程传参技巧

作用:resume与yield双向传参,实现数据交互

local co = coroutine.create(function(a)
    print("初始参数:", a)
    local b = coroutine.yield("第一次返回")
    print("恢复参数:", b)
end)

coroutine.resume(co, 100)
coroutine.resume(co, 200)

七、模块化与代码解耦

1. 标准模块封装写法

作用:规范模块导出,隔离全局环境,工程化开发必备

-- 新建 tool.lua 模块文件
local Tool = {}
Tool.__index = Tool

-- 私有函数(外部无法访问)
local function log(str)
    print("[日志]", str)
end

-- 公开函数
function Tool:add(a,b)
    log("执行加法")
    return a + b
end

return Tool

-- 主文件调用
-- local Tool = require("tool")
-- print(Tool:add(1,2))

2. 模块卸载与重载

作用:解决require缓存问题,支持热更新

-- 卸载模块
package.loaded["tool"] = nil
-- 重新加载
local Tool = require("tool")

八、错误处理与调试高阶

1. assert 断言

作用:条件不成立直接报错,用于参数校验

local num = nil
assert(num, "变量不能为空!")

2. xpcall 带栈追踪捕获错误

作用:比pcall多堆栈信息,精准定位报错位置

local function errHandler(err)
    return err .. "\n" .. debug.traceback()
end

local ok, res = xpcall(function()
    print(1/0)
end, errHandler)

if not ok then
    print("错误详情:", res)
end

3. debug 调试库

作用:查看函数栈、局部变量,高阶调试排错

local function test()
    local a = 100
    print(debug.localvars(1)) -- 打印当前函数局部变量
end
test()

九、字符串与正则进阶

作用:Lua原生正则(模式匹配),无需第三方库

local s = "Lua123Python456"

-- 匹配数字
print(string.match(s, "%d+"))
-- 匹配字母
print(string.match(s, "%a+"))
-- 全局替换
print(string.gsub(s, "%d", ""))
-- 查找所有匹配
for v in string.gmatch(s, "%d+") do
    print(v)
end

十、GC内存优化(工程必备)

作用:控制垃圾回收,优化游戏/长驻程序内存

collectgarbage("stop")  -- 停止GC
collectgarbage("restart")-- 重启GC
collectgarbage("count") -- 获取当前内存占用(KB)
collectgarbage()        -- 手动全量回收

print("当前内存:", collectgarbage("count"))

Python 极简完整教程(全知识点+纯用法)

说明:全文无冗余描述,每项只写:作用 + 标准代码写法,可直接复制运行。覆盖Python入门到进阶全部核心知识点。

一、基础语法规则

1. 注释

作用:代码备注,不执行

# 单行注释

"""
多行注释
多行注释
"""

'''
多行注释
多行注释
'''

2. 语句规则

作用:代码书写规范

  • Python 禁止随意缩进,缩进代表代码块(4个空格/1个Tab)
  • 大小写敏感:a 和 A 是两个变量
  • 语句结尾无需分号(可加但不推荐)
  • 标识符:字母/下划线开头,后跟字母、数字、下划线,不能用关键字

3. 打印输出

作用:控制台打印内容

print("Hello Python")
print(123, True, None)
# 换行/不换行
print("默认换行")
print("不换行", end="")

二、六大核心数据类型

作用:存储各类数据,type()查看数据类型

# 1. None 空值
a = None

# 2. bool 布尔
b = True
c = False

# 3. 数字类型(int整数 / float小数 / complex复数)
d = 100    # int
e = 3.14   # float
f = 1+2j   # complex

# 4. str 字符串
str1 = "双引号"
str2 = '单引号'
str3 = """
多行
字符串
"""

# 5. 序列/容器类型
list1 = [1,2,3]      # 列表
tuple1 = (1,2,3)     # 元组
dict1 = {"name":"py"}# 字典
set1 = {1,2,3}       # 集合

# 查看类型
print(type(a))
print(type(str1))

三、变量与赋值

作用:存储数据,Python变量无声明关键字,动态类型

# 单个赋值
num = 100

# 多变量赋值
a, b, c = 1, 2, 3

# 批量同值赋值
x = y = z = 666

# 变量交换(无需中间变量)
m, n = 10, 20
m, n = n, m

# 动态类型:可随意变更变量类型
var = 123
var = "字符串"

四、运算符

1. 算术运算符

a = 10
b = 3
print(a + b)   # 加
print(a - b)   # 减
print(a * b)   # 乘
print(a / b)   # 浮点除
print(a // b)  # 整除(向下取整)
print(a % b)   # 取余
print(a ** b)  # 幂运算
print(-a)      # 负号

2. 关系运算符

返回 True/False

print(10 == 10)  # 等于
print(10 != 3)   # 不等于
print(10 > 3)    # 大于
print(10 < 3)    # 小于
print(10 >= 3)   # 大于等于
print(10 <= 3)   # 小于等于

3. 逻辑运算符

print(True and False)  # 与
print(True or False)   # 或
print(not True)        # 非

# 短路赋值技巧
n = None
res = n or 100  # 空值则取默认值100

4. 成员/身份运算符

# 成员运算符 in / not in
lst = [1,2,3]
print(1 in lst)
print(4 not in lst)

# 身份运算符 is / is not(判断内存地址)
a = [1,2]
b = [1,2]
print(a is b)
print(a == b)

五、流程控制

1. if 条件判断

# 单分支
a = 10
if a > 5:
    print("大于5")

# 双分支
if a > 20:
    print("大")
else:
    print("小")

# 多分支
if a < 5:
    print("小")
elif a < 15:
    print("中")
else:
    print("大")

# 三元表达式(极简判断)
res = "是" if a > 5 else "否"

2. for 循环

# 基础数值循环
for i in range(1, 6):  # 1-5,左闭右开
    print(i)

# 带步长循环
for i in range(1, 10, 2):
    print(i)

# 遍历字符串/列表
for char in "python":
    print(char)

for item in [11,22,33]:
    print(item)

3. while 循环

i = 1
while i <= 3:
    print(i)
    i += 1

# 无限循环
# while True:
#     print("循环")

4. 循环跳转

# break 跳出整个循环
for i in range(1,10):
    if i == 3:
        break
    print(i)

# continue 跳出本次循环,继续下一次
for i in range(1,10):
    if i == 3:
        continue
    print(i)

六、函数(核心)

作用:封装代码、复用逻辑、简化代码

1. 基础函数

# 定义
def add(a, b):
    return a + b

# 调用
print(add(2, 3))

2. 参数类型

# 默认参数
def func1(a, b=10):
    return a + b

# 关键字参数
func1(a=5, b=20)

# 可变位置参数 *args(接收元组)
def func2(*args):
    print(args)

func2(1,2,3)

# 可变关键字参数 **kwargs(接收字典)
def func3(**kwargs):
    print(kwargs)

func3(name="py", age=20)

3. 多返回值

def get_pos():
    return 10, 20

x, y = get_pos()
print(x, y)

4. 匿名函数 lambda

# 单行极简函数
f = lambda a,b: a * b
print(f(2,5))

七、四大容器精讲

1. 列表 list(有序、可变、可重复)

# 定义
lst = [1,2,3,"py"]

# 增删改查
lst.append(4)        # 尾部添加
lst.insert(1, 99)    # 指定位置插入
lst.pop()            # 删除末尾
lst.remove(99)       # 指定元素删除
lst[0] = 100         # 修改元素
print(lst[0])        # 索引取值

# 切片
print(lst[1:3])      # 1-2位
print(lst[::-1])     # 反转列表

# 常用方法
print(len(lst))      # 长度
lst.sort()           # 排序
lst.reverse()        # 反转

2. 元组 tuple(有序、不可变、可重复)

# 定义
tup = (1,2,3)
tup2 = (1,)  # 单个元素必须加逗号

# 查(无修改删除方法)
print(tup[0])
print(len(tup))

3. 字典 dict(无序、可变、键唯一)

# 定义
d = {"name":"python", "age":20}

# 增改查
print(d["name"])             # 取值
print(d.get("sex", "未知"))  # 安全取值
d["version"] = 3.10          # 新增键值对
d["age"] = 21                # 修改值

# 删除
del d["version"]

# 遍历
print(d.keys())   # 所有键
print(d.values()) # 所有值
print(d.items())  # 所有键值对

4. 集合 set(无序、可变、元素唯一)

# 定义(自动去重)
s = {1,2,2,3}

# 增删
s.add(4)
s.remove(3)

# 集合运算
a = {1,2,3}
b = {3,4,5}
print(a & b)  # 交集
print(a | b)  # 并集
print(a - b)  # 差集

八、字符串常用操作

s = "PythonStudy"

print(len(s))          # 字符串长度
print(s.upper())       # 转大写
print(s.lower())       # 转小写
print(s.strip())       # 去除首尾空格
print(s.find("Py"))    # 查找下标
print(s.replace("Py","Go")) # 替换
print(s.split("t"))    # 分割成列表
print(s[0:3])          # 切片截取

# 字符串格式化
name = "python"
print(f"语言:{name}")  # f-string(推荐)
print("语言:%s" % name)

九、迭代遍历

# 遍历列表(带下标)
lst = [11,22,33]
for idx, val in enumerate(lst):
    print(idx, val)

# 遍历字典
d = {"a":1, "b":2}
for k, v in d.items():
    print(k, v)

十、变量作用域

# 全局变量
num = 10

def test():
    global num  # 声明使用全局变量
    num = 20
    print(num)

test()
print(num)

# 局部变量:仅函数内部生效
def func():
    a = 100
    print(a)
# print(a) 外部无法访问

十一、异常处理

作用:捕获错误,防止程序崩溃

try:
    # 可能报错的代码
    print(1 / 0)
except ZeroDivisionError:
    print("除数不能为0")
except Exception as e:
    print("未知错误:", e)
else:
    print("无异常时执行")
finally:
    print("无论是否报错都执行")

十二、模块与包

作用:导入内置/第三方/自定义模块,复用代码

# 导入完整模块
import math
print(math.pi)
print(math.sqrt(4))

# 导入指定功能
from math import pow
print(pow(2,3))

# 别名导入
import math as m

# 导入自定义模块
import test

十三、文件IO操作

# 写入文件(w覆盖 / a追加)
with open("test.txt", "w", encoding="utf-8") as f:
    f.write("测试写入内容")

# 读取文件
with open("test.txt", "r", encoding="utf-8") as f:
    text = f.read()
    print(text)

# 按行读取
with open("test.txt", "r", encoding="utf-8") as f:
    for line in f.readlines():
        print(line.strip())

十四、面向对象(Python核心)

作用:封装、继承、多态,模块化编程

1. 基础类与实例

# 定义类
class Person:
    # 构造方法(初始化)
    def __init__(self, name, age):
        self.name = name
        self.age = age

    # 成员方法
    def say(self):
        print(f"姓名:{self.name},年龄:{self.age}")

# 实例化对象
p = Person("小明", 18)
p.say()

2. 类继承

# 子类继承父类
class Student(Person):
    def __init__(self, name, age, stu_id):
        super().__init__(name, age) # 调用父类构造
        self.stu_id = stu_id

    def study(self):
        print(f"{self.name}正在学习")

s = Student("小红", 16, "001")
s.say()
s.study()

十五、常用高阶语法

1. 列表推导式(极简生成列表)

# 生成1-10偶数列表
lst = [x for x in range(1,11) if x % 2 == 0]
print(lst)

2. map/filter 高阶函数

# map:批量处理元素
lst = [1,2,3]
res = list(map(lambda x:x*2, lst))
print(res)

# filter:过滤元素
res2 = list(filter(lambda x:x>1, lst))
print(res2)

十六、迭代器与生成器

# 生成器(节省内存)
def gen():
    yield 1
    yield 2
    yield 3

g = gen()
print(next(g))
print(next(g))

十七、多线程/多进程(简易用法)

# 简易多线程
import threading
import time

def task():
    print("线程执行")
    time.sleep(1)

t = threading.Thread(target=task)
t.start()
t.join()

python进阶版

Lua 极简完整教程(全知识点+纯用法)

说明:全文无冗余描述,每项只写:作用 + 标准代码写法,可直接复制运行。覆盖Lua入门到进阶全部核心知识点。

一、基础语法规则

1. 注释

作用:代码备注,不执行

-- 单行注释

--[[
多行注释
多行注释
]]

2. 语句规则

作用:代码书写规范

  • Lua 可省略分号,不报错
  • 大小写敏感:a 和 A 是两个变量
  • 标识符:字母/下划线开头,后跟字母、数字、下划线

3. 打印输出

作用:控制台打印内容

print("Hello Lua")
print(123, true, nil)

二、八大数据类型

作用:Lua所有数据仅有8种类型,type()查看类型

-- 1. nil 空值(默认未赋值变量)
local a = nil

-- 2. boolean 布尔
local b = true
local c = false

-- 3. number 数字(整数/小数统一类型)
local d = 100
local e = 3.14

-- 4. string 字符串
local str1 = "双引号字符串"
local str2 = '单引号字符串'
local str3 = [[
多行
字符串
]]

-- 5. table 表(数组+字典,Lua唯一容器)
local t = {}

-- 6. function 函数
local f = function() end

-- 7. userdata 自定义C数据(极少用)
-- 8. thread 协程线程

-- 查看类型
print(type(a)) -- nil
print(type(str1)) -- string

三、变量(全局/局部)

作用:存储数据,局部变量优先使用(效率高、不污染全局)

-- 全局变量:任意位置访问,默认全局
g_num = 100

-- 局部变量:仅当前代码块有效,local声明
local l_num = 200

-- 多变量赋值
local x, y, z = 1, 2, 3

-- 变量默认值 nil
local empty
print(empty) -- nil

四、运算符

1. 算术运算符

local a = 10
local b = 3
print(a + b)  -- 加
print(a - b)  -- 减
print(a * b)  -- 乘
print(a / b)  -- 除(浮点)
print(a % b)  -- 取余
print(a ^ b)  -- 幂运算
print(-a)     -- 负号

2. 关系运算符

返回 true/false

print(10 == 10)  -- 等于
print(10 ~= 3)   -- 不等于(Lua独有 ~=)
print(10 > 3)   -- 大于
print(10 < 3)   -- 小于
print(10 >= 3)  -- 大于等于
print(10 <= 3)  -- 小于等于

3. 逻辑运算符

Lua逻辑:and / or / not,无\&\& || \!

print(true and false) -- 与
print(true or false)  -- 或
print(not true)       -- 非

-- 短路特性(常用赋值技巧)
local n = nil
local res = n or 100 -- n为空则取100(默认值赋值)

4. 字符串拼接

符号:..

local s = "Lua" .. "学习"
print(s) -- Lua学习

五、流程控制

1. if 条件判断

-- 单分支
local a = 10
if a > 5 then
    print("大于5")
end

-- 双分支
if a > 20 then
    print("大")
else
    print("小")
end

-- 多分支
if a < 5 then
    print("小")
elseif a < 15 then
    print("中")
else
    print("大")
end

2. for 循环

-- 数值for:起始,结束,步长(步长默认1)
for i=1,5 do
    print(i) -- 1 2 3 4 5
end

for i=1,10,2 do
    print(i) -- 1 3 5 7 9
end

3. while 循环

local i = 1
while i <= 3 do
    print(i)
    i = i + 1
end

4. repeat until 循环

特点:先执行后判断,至少执行一次

local i = 1
repeat
    print(i)
    i = i + 1
until i > 3

5. 循环跳转

-- break:跳出当前循环
for i=1,10 do
    if i == 3 then
        break
    end
    print(i)
end

-- Lua 无 continue,可通过 if 模拟

六、函数(核心)

作用:封装代码,复用逻辑,支持多返回值

1. 基础函数

-- 定义
local function add(a,b)
    return a + b
end

-- 调用
print(add(2,3)) -- 5

2. 多返回值

local function getPos()
    return 10, 20
end
local x,y = getPos()
print(x,y)

3. 可变参数

作用:接收任意多个参数

local function sum(...)
    local res = 0
    for _,v in ipairs({...}) do
        res = res + v
    end
    return res
end
print(sum(1,2,3,4))

4. 匿名函数

local f = function(a,b)
    return a*b
end
print(f(2,5))

七、Table 表(Lua万能容器)

作用:唯一的数据容器,可当数组、字典、对象、结构体使用

1. 数组(有序列表,默认下标从1开始)

local arr = {"a","b","c"}
print(arr[1]) -- a
-- 遍历数组
for i,v in ipairs(arr) do
    print(i,v)
end

2. 字典(键值对)

local dict = {
    name = "Lua",
    age = 20
}
print(dict.name)
print(dict["age"])

-- 增改
dict.version = 5.4
-- 删除
dict.age = nil

3. 混合表 + 遍历

local t = {10,20,name="测试"}

-- 遍历所有键值对(万能遍历)
for k,v in pairs(t) do
    print(k,v)
end

4. 常用表操作

local arr = {1,2,3}
table.insert(arr,4)    -- 尾部插入
table.insert(arr,2,99) -- 指定下标插入
table.remove(arr,2)    -- 删除指定下标
print(#arr)            -- # 获取数组长度

八、字符串常用操作

local s = "LuaStudy"
print(#s)                 -- 字符串长度
print(string.upper(s))    -- 转大写
print(string.lower(s))    -- 转小写
print(string.find(s,"Lua"))-- 查找子串位置
print(string.sub(s,1,3))  -- 截取 1-3位
print(string.rep(s,2))    -- 重复2次
print(string.gsub(s,"Lua","Go")) -- 替换

九、迭代器遍历

  • ipairs:只遍历数字下标、连续数组,从1开始
  • pairs:遍历所有键值对(数组、字典全部遍历)
local t = {11,22,name="test"}
for i,v in ipairs(t) do print(i,v) end
for k,v in pairs(t) do print(k,v) end

十、作用域

作用:区分变量生效范围

local a = 10 -- 全局局部(文件级)
if true then
    local a = 20 -- 代码块局部,仅内部生效
    print(a) -- 20
end
print(a) -- 10

十一、异常处理

作用:捕获代码错误,防止程序崩溃

local ok, err = pcall(function()
    -- 可能报错的代码
    print(1/0)
end)
if not ok then
    print("错误:",err)
end

十二、模块与require

作用:引入外部lua文件,代码模块化

-- 引入同目录模块
local m = require("test")
-- 卸载模块
package.loaded["test"] = nil

十三、协程(Lua核心特性)

作用:轻量级线程,可暂停、恢复执行

-- 创建协程
local co = coroutine.create(function()
    print("协程执行")
    coroutine.yield() -- 暂停
    print("协程恢复")
end)

coroutine.resume(co) -- 启动
coroutine.resume(co) -- 恢复

十四、常用系统工具

-- 随机数
math.randomseed(os.time()) -- 随机种子
print(math.random(1,10))

-- 数学函数
print(math.floor(3.9)) -- 向下取整
print(math.ceil(3.1))  -- 向上取整
print(math.max(1,9))

-- 获取当前时间
print(os.time())

十五、元表与元方法(进阶)

作用:给table添加重载行为、自定义操作

local t1 = {1,2}
local mt = {
    __add = function(a,b)
        return {a[1]+b[1], a[2]+b[2]}
    end
}
setmetatable(t1,mt)
local t2 = {3,4}
local res = t1 + t2 -- 重载加法
print(res[1],res[2])

十六、面向对象(Lua模拟)

作用:用table+元表实现类与继承

-- 定义类
local Person = {}
Person.__index = Person

-- 构造方法
function Person.new(name,age)
    local self = setmetatable({},Person)
    self.name = name
    self.age = age
    return self
end

-- 成员方法
function Person:say()
    print(self.name,self.age)
end

-- 实例化
local p = Person.new("小明",18)
p:say()

十七、文件IO

-- 写文件
local f = io.open("test.txt","w")
f:write("测试内容")
f:close()

-- 读文件
local f = io.open("test.txt","r")
local str = f:read("*a")
print(str)
f:close()

lua进阶版