【Unity】Lua热更新 笔记 (一)

热更新

前言

  这是个人学习笔记,仅供参考。

一、认识更新方式

描述适用于原因
传统重新下载最新游戏客户端包体PC耗电大、耗时长
现在热更新PC/Andriod/ios耗时短,适用于手机端

二、什么是热更新

答:
 (1)游戏上线后,在运营过过程中,如果需要更换UI显示,或者修改游戏的逻辑行为。传统的更新模式下,需要重新打包游戏,让玩家重新下载包体,造成用户体验不佳的情况。
 (2)热更新允许在不重新下载游戏客户端的情况下,更新游戏内容。

三、如何使用更新

答:两种更新方式混合使用。

四、如何热更新

4.1 认识AssetBundle

  Unity提供的一种资源更新技术,通过使用AssetBundle更新资源,也可以通过把脚本或者其他代码作为资源(可理解所有游戏资源)打包成AssetBundle然后更新到客户端。

4.2 C#脚本能不能直接更新

  C#运行之前需要先编译,编译过程无法在手机上完成。当我们的游戏逻辑更改时,即C#代码内容发生改变时,需要重新发布新版本。这对于手游来说是体验欠佳的。

  C#的编译流程:写好的代码->编译成.dll扩展程序(UnityEditor完成)->运行于Unity

4.3 热更新有哪些实现方式

   - 使用 Lua 脚本编写游戏的 UI 或者 其他逻辑 (调用C#中的方法进行)
   - 使用 C#Light 【方案不成熟、效率低】

4.4 如何使用Lua进行热更新

  在移动端中编写Lua解析器,通过解析器运行最新的Lua脚本,然后开发人员将控制游戏逻辑的代码写成Lua脚本。

  Lua的解析
  - uLua
  - Nlua
  - UniLua
  - sLua
   xLus = sLua + 代码注入补丁 + 完善工具链 + 腾讯【关注】

4.5 学习热更新路线

   - Lua编程
   - LuaInterface和luanet进行Lua和C#的交互通信
   - 学习使用AssetBundle进行资源更新
   - 学习uLua LuaFramework

五、Lua语言

5.1 认识Lua

  • Lua是一个小巧的脚本语言,由标准C编写而成,在所有操作系统和平台上均可以编译与运行。
  • Lua没有提供强大的库。
  • Lua有一个同时进行的JIT项目,提供在特定平台上的及时编译功能。

5.2 下载Lua

  官方下载地址:Lua官网
  GitHub下载地址:Lua for Windows

5.3 Lua文本格式

  后缀名严格要求:.type.lua

5.4 关键字

12345678910
andbreakdoelseelseifendfalseforfunctionif
inlocalnilnotorrepeatreturnthentrueuntil

  其中nil=C#中的null

5.5 行注释

单行注释:–

--这是一个注释演示

多行注释:–[[ --]]

--[[
这是第一行注释
这是第二行注释
这是第三行注释
--]]

  PS:快捷 使用/取消 注释:Ctrl+Q

5.6 数据类型

  Lua是动态类型语言,变量不需要类型定义。

数据类型描述
nil无效值,形同于C#中的null(在条件表达式中相当于false)
boolean包含两个值:true 和 false(只有false和nil为假,其余均为真)
number表示双精度类型的实浮点数
string字符串,由一对双引号或单引号来表示(不可修改)
function由C或Lua编写的函数
userdata便是任意存储在变量中的C数据结构
thread表示执行的独立线路,用于执行协同程序(协程)
tableLua中的表(table)其实是一个"关联数组",数组的索引可以是数字或字符串,在Lua中,table的创建是通过"构造表达式"来完成,最简单构造表达式“{}”,用来创建一个空表
5.6.1 字符串替换

  Lua中的string不可以修改。

--string
a = "one string"
--gsub() 替换字符串,将对象a中的one替换为another
b = string.gsub(a, "one", "another")
5.6.2 连接字符串
-- ".." 相当于C语言中的"+"
c = a .. "," .. b 
5.6.3 C#与Lua的加法

  C#中 "10" + 2的结果为102,即转换为字符串相加。
  Lua中"10" + 2的结果为12,即转换为number。

print(10 + 2)
print("10" + 2)
5.6.4 ==比较
print(10 == "10") --false
print(tostring(10) == "10") --true
print(10 .. "" == "10") --true

  注意:Lua中..写在number后,需要加空格告诉Lua这是一个连接字符串。

5.6.5 条件判断语句
if exp then
	block
elseif exp then 
	block
else
	block
End

exp:判断条件
block:内容

  Lua认为false、nil为假;true/非nil为真。特别注意的是Lua中的0为true。

练习:判断年份是闰年或平年
提示:~=:不等于 not:非 and:和 or:或

year = 2020
if (year % 4 == 0 and year % 100 ~=0) or year % 400 = 0 then
	print(year .. "是闰年")
else
	print(year .. "是平年")
end
5.6.6 For循环语句

  Lua没有switch-case语句

--for
for i=1, 10, 1 do
	pirnt(i)
end

for i=10, 1, -1 do
	pirnt(i)
end

  注意:Lua中的for循环包含10

练习:输出矩阵{[1,2,3,4,5],[2,4,6,8,10],[3,6,9,12,15],[4,8,12,16,20]}

str = ""
for j=1, 4, 1 do
	for i=1, 5, 1 do
		str = str .. i*j .. " "
	end
end
print(str)
5.6.7 While循环语句
--while
a = 1
while(a < 10) do
	print(a)
	a = a + 1
end
5.6.8 Function 函数
--func
print(add(2 ,3)) --查找不到App

-- local相当于局部变量
local function add(a, b)
	return a + b
end

print(add(2 ,3))

  注意:使用某一模块或函数,须先加载这个模块和函数,在后面调用。

5.6.9 数据输入
--io.read()获取输入值
local a = io.read()
local b = io.read()

print(a .. "+" .. b .. "=" .. add(a,b)) 

练习:实现简单的两个数的加减乘除

function add(a ,b) return a + b end
function subtract(a ,b) return a - b end
function multiply(a ,b) return a * b end
function divide(a ,b) return a / b end

function calculate(a, b, operator)
	if operator == "+" then
		return add(a,b)
	elseif operator = "-" then
		return subtract(a, b)
	elseif operator = "*" then
		return multiply(a, b)
	elseif operator = "/" then
		return divide(a, b)
	else
		return "非法运算符"
	end
end

local a = io.read()
local operator = io.read()
local b = io.read()

print(a .. operator .. b .. "=" ..calculate(a, b, operator))

练习题代码改进
  思路:通过输入运算符号,再传入数值计算。

function add(a ,b) return a + b end
function subtract(a ,b) return a - b end
function multiply(a ,b) return a * b end
function divide(a ,b) return a / b end
function default(a ,b) return "非法运算符" end

function calculate(a, b, operator)
	if operator == "+" then return add
	elseif operator = "-" then return subtract
	elseif operator = "*" then return multiply
	elseif operator = "/" then return divide
	else
		return dafault
	end
end

local a = io.read()
local operator = io.read()
local b = io.read()
local function = calculate(operator)

print(a .. operator .. b .. "=" ..calculate(a, b, operator))
5.6.10 参数
function test(n)
--~	if n == nil then
--~		n=0
--~	end
	n = n or 0
	print(n)
end

test(3) --3
test()  --nil
test(3, 4) --3

  注意:对于未输入确切值,C#会报错,但Lua会输出结果 nil

阶段练习

题目:1/1! + 1/2! + 1/3! + … + 1/20! = ?

local function fact(n)
	if n == 1 then
		return 1
	else
		return n*fact(n-1)
	end
end

local function sum(n)
	local s = 0
	for i=1, n, 1 do
		s = s + 1/fact(i)
	end
	return s
end
5.6.11 变长参数
local function test(...)
	local arr = {...}  --数组
	print("test参数个数:" .. #arr)

--~	for i=1, #arr, 1 do
--~		print(arr[i])
--~	end
	
	for index, value in ipairs(arr) do
		print(index, value)
	end
end

test(1)
test("a", true)

  Lua中数组:local arr = {...}
  数组长度:#arr
  迭代数组方法: ipairs()

5.6.12 返回值
local function init()
	return 1, "hi"
end

local a,b = init()
print(a, b) -- a  b  对应  1  hi 

local a,b,c = init(),"c"
print(a, b, c) -- a b c 对应 1 c nil

local a,b,c = "c",init()
print(a, b, c) -- a b c 对应 c 1 hi

5.7 Table表

5.7.1 初始化方式
--table
local t = {["color"] = "red", price = 6} --初始化01
t["Name"] = "Apple" --初始化02
t,weight = 0.3 --初始化03

print(t["price"], t.name) --对应 6 Apple

  - 初始化:["color"] = "red" 等价于 t["Name"] = "Apple"
  - local arr = {"a", "b", "c"}实质上是table表。等价于 arr = { [1] = “a”, [2] = “b”, [3] = “c”}
  - Lua中无数组。

5.7.2 ipairs( )与pairs( )
arr = {
	[1] = "a",
	[2] = "b", 
	[3] = "c"
}

for key,value in ipairs(t) do
	print(key,value)
end
--仅能读出表 [1]
for key,value in pairs(t) do
	print(key,value)
end

  ipairs():适用于有顺序的数据表,遇到无序表将无法读出。
  pairs():无论是否有序,均能读出。

续文:Lua热更新 笔记(二)

  • 5
    点赞
  • 21
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值