Lua中的数据类型——string

string 进阶

Lua中有三种方式表达一个字符串 :

  • 用单引号包围 : ' string ' ;
  • 用双引号包围 : " string " ;
  • 用双中括号包围 : [[ string ]] ;

为了方便地使用字符串 , Lua提供了如下”功能” :

  • 转义字符 : 转义字符用于表示字符串中不能直接显示的字符 ;
  • 成员方法 : string类有很多实用的成员方法 ;
  • 格式化 : 类似C中printf()的字符串格式化 , 常用于string.format()方法;
  • 匹配模式 : 类似正则表达式一样的匹配 , 常用于string.find(), string.gmatch(), string.gsub(), string.match()方法 ;

转义字符

Lua中字符串的转义字符与C/C++一样 , 都是一个\加上特殊的字符 . 个别语法上有些许差别 .

转义字符 意义 ASCII码 (十进制)
\a 响铃 (BEL) . 让系统发出一个提示音 007
\b 退格 (BS) . 将当前位置移动到前一列 008
\f 换页 (FF) . 将当前位置移动到下一页开头 012
\n 换行 (CR) . 将当前位置移动到下一行开头 010
\r 回车 (CR) . 将当前位置移动到本行开头 013
\t 水平制表 (HT) . 跳到下一个TAB位置 009
\v 垂直制表 (VT) 011
\\ \ 一个放斜杠字符 092
\‘ 一个单引号字符 039
\“ 一个双引号字符 034
\0 空字符 (NULL) 000
\ddd 1-3位八进制数 (d代表数字 , 数量可调整) 3位八进制
\xhh 1-2位十六进制数 (h代表数字 , 数量可调整) 2位十六进制

string成员方法

Lua提供了string类 , 其有很多实用的成员方法提供对字符串的操作 . (这里的string不是代指某一字符串 , 而是一个类叫做string)

string.upper(s) / string.lower(s)

转换大小写 . 前者将参数字符串s转换为大写字母并返回 , 后者将参数字符串s转换为小写字母并返回 .

1
2
string.upper("qwerty")  --> 返回 QWERTY
string.lower("QWERTY") --> 返回 qwerty

string.gsub(s, pattern, repl, [n])

替换字符串 . s字符串中npattern字符替换为repl字符 , n缺省为#str(替换全部) .

1
string.gsub("aaaa", "a", "z", 3)  --> 返回 zzza

string.find(s, pattern, [init], [plain])

搜索字符串 . 在s中从init处开始搜索第1个出现的pattern, 返回其起始位置和结束位置 . init缺省1, plain不知道啥用 .

1
string.find("Hello Lua user", "Lua ", 1)  --> 返回 7 10 (匹配的是"Lua "有一个空格)

string.reverse(s)

反转字符串 . 将参数字符串s反转后返回 .

1
string.reverse("Lua") --> 返回 auL

string.format(s, …)

字符串格式化 . 类似C中的printf() , 但结果作为返回值返回而不是输出 .

1
string.format("the value is : %d", 4) --> 返回 the value is : 4 (是返回不是输出)

string.char(byte, …) / string.byte(s, [i], [j])

字符串转换 . 前者将整型按照ASCII码转换为字符并拼接 , 后者将字符串s的第ij个字符转换为整型 .
(string.byte中 : i缺省1, j缺省i, 负数表示从末尾开始的某个字符)

1
2
3
4
string.char(97, 98, 99, 100)  --> 返回 abcd
string.byte("ABCD") --> 返回 68
string.byte("ABCD", 4) --> 返回 65
string.byte("ABCD", 2, 4) --> 返回 66 67 68

string.len(s)

计算长度 . 返回参数字符串s的长度 .

1
string.len("qwer")  --> 返回 4

string.rep(str, n) string.rep(s, n, [sep])

拷贝字符串 . 返回字符串sn个拷贝, 以字符串sep为分隔符 . sep默认为nil(没有分隔符)

1
string.rep("abc", 2)  --> 返回 abcabc

string.sub(s, i, [j])

截取字符串 . 截取字符串s的第i到第j个字符, j缺省-1表示最后一个 , i若为负数则表示从末尾第-i个字符开始 .

1
string.sub("qwerty", -2)  --> 返回 ty (-2表示截取末尾两个)

string.match(str, pattern, [init]) string.match(s, pattern, [init])

查找配对 . 返回s字符串的第一个符合pattern描述的子集的 , init表示查找的起点 , 缺省为1 .

1
print(string.match("Hello Lua user", "%a+", 2)) --> 返回 ello

string.gmatch(str, pattern) string.gmatch(s, pattern, [init])

迭代查找配对 . 每调用一次 , 返回s字符串的下一个符合pattern描述的子集的 迭代器 , init表示查找的起点 , 缺省为1 .

1
2
3
4
5
for word in string.gmatch("Hello Lua user", "%a+") do print(word) end
--[[输出
Hello
Lua
user]]

字符串格式化

string.format(s, ...)方法使用类似C中printf()的格式化方法 , 其占位符也与C中的差不多 .

字符串格式化的占位符包括 :

占位符 含义
%c 字符 . 接受一个数字 , 并转为ASCII码对应的字符
%d / %i 有符号整数 . 接受一个数字 , 并转为有符号整数
%u 无符号整数 . 接受一个数字 , 并转为无符号整数
%o 八进制数 . 接受一个数字 , 并转为八进制数
%x / %X 十六进制数 . 接受一个数字 , 并转为十六进制数 . 前者用小写字母 , 后者用大写字母
%e / %E 科学记数法 . 接受一个数字 , 并转为科学计数法 . 前者用小写字母 , 后者用大写字母
%f 浮点数 . 接受一个数字 , 并转为浮点数
%g / %G 科学计数法/浮点数中简短者 . 接受一个数字 , 并转为%e/%E及%f中简短的一种格式
%s 字符串 . 接受一个字符串 , 并按照给定的参数格式化该字符串
%q 安全字符串 . 接受一个字符串 , 并转为克被Lua编译器安全读入的格式

占位符的进一步细化 , 在%后添加参数 :

  • 符号 : 一个 + 表示显示正数的正号
  • 占位符 : 一个 0 表示该字串至少占用的位置
  • 对齐标识 : 一个 - 表示该字串左对齐 , 默认右对齐 . 使用这个的前提是指定了字串宽度
  • 宽度数值 : 一个 数字 表示该字串的显示宽度(不足补空格)
  • 小数位数/字串裁切 : 一个 .数字 表示该字串显示的长度 , 若为浮点数则表示保留的小数位数

匹配模式

在方法string.find(), string.gmatch(), string.gsub(), string.match()中 , 可以使用匹配字串 .
Lua中的匹配字串直接用常规的字符串描述 , 匹配字串方便我们筛选需要的字符串 .

Lua支持的所有字符类

字符类 描述
单个字符 单个字符 . 与该字符自身配对 , 但 ^ $ ( ) % . [ ] * + - ? 除外
. 一个字符 . 与任何字符配对
%a 一个字母 . 与任何字母配对
%c 一个控制字符 . 与任何控制字符配对 (如 \n )
%d 一个数字 . 与任何数字配对
%l 一个小写字母 . 与任何小写字母配对
%u 一个大写字母 . 与任何大写字母配对
%w 一个数字或字母 . 与任何数字或字母配对
%p 一个标点 . 与任何标点配对
%s 一个空白 . 与空白字符配对
%x 一个十六进制数 . 与任意十六进制数配对
%z 一个0 . 与任何代表0的字符配对
%(^$()%.[]*+-?) 一个特殊字符 . 与(^$()%.[]*+-?)这些字符自身配对
[数个字符类] 括号中的任意值 . 例如[%l_]与一个小写字母或一个_配对
[^数个字符类] 非括号中的任意值 . 例如[%l_]与一个小写字母或一个_除外的字符配对

匹配模式的进一步细化 , 模式条目 :

  • 单个字符类匹配该类别中的任意单个字符 ;
  • 单个字符类跟一个 * , 表示匹配0个或多个的该类字符 , 优先匹配最长的 ;
  • 单个字符类跟一个 + , 表示匹配1个或多个的该类字符 , 优先匹配最长的 ;
  • 单个字符类跟一个 - , 表示匹配0个或多个的该类字符 , 优先匹配最短的 ;
  • 单个字符类跟一个 ? , 表示匹配0个或1个的该类字符 , 优先匹配1个的 ;