美文网首页LPC-tutorial
LPC语言基本变量类型

LPC语言基本变量类型

作者: 秋林拾叶 | 来源:发表于2019-04-25 18:41 被阅读0次

本文节选自本人写作的《 LPC 语言基础教程:从零学习游戏开发》第二章第一节。

第一节 LPC语言基本变量类型

LPC语言的数据类型基本和C语言类似,但是和C语言相同和相似的数据类型只有:整型(int)、浮点型(float)、字符串(string)、数组(array)、结构体(class)。

1. 有符号整型(int)

在C语言中的整数分 short、int、long,还有无符号数 unsigned,但在LPC语言中,只有 int 类型

在 fluffos 驱动中,int 的长度是8个字节,长度和C语言64 位 Linux 及 Mac OS 下的长整型一样,取值范围是-263 ~ 263-1,即-9223372036854775808~9223372036854775807。

在C语言中,如果数值超出取值范围会超成数据溢出,如下C语言代码,在64位 Linux 系统下,因为溢出,输出结果变成:-9223372036854775808

#include <stdio.h>
int main()
{
    long i = 9223372036854775808;
    printf("%ld\n", i);
    return 0;
}

但是在LPC中,对数据溢出的处理方式不太一样,如果变量赋值超出最大值,取最大值,如果赋值小于最小值,取最小值(截止2019-04-20,fluffos最小值有BUG,实际值为-9223372036854775807),但是对赋值后的变量做运算,会和C语言一样的溢出。

我们修改 test.c 的代码如下:

int main(object me, string arg)
{
    // MAX_INT、MIN_INT 为 fluffos 定义宏
    int a = MAX_INT, b = MIN_INT;
    // 赋值时做运算
    int c = MAX_INT + 1, d = MIN_INT - 1, e = d - 1;
    // 赋值超出取值范围(10倍)
    int f = 92233720368547758070, g = -92233720368547758080;
    printf("a = %d\nb = %d\nc = %d\nd = %d\ne = %d\nf = %d\ng = %d\n", a, b, c, d, e, f, g);
}

然后输入指令 test ,输出结果如下:

a = 9223372036854775807
b = -9223372036854775807
c = -9223372036854775808
d = -9223372036854775808
e = 9223372036854775807
f = 9223372036854775807
g = -9223372036854775807

代码中的 MAX_INTMIN_INT 是 fluffos 宏定义的整形最大值和最小值,变量 a、f都取最大值,变量 b、g都取最小值,但从结果看,最小值输出比实际大了1,这是 fluffos 的 BUG。变量 c 运算后溢出,变量 d 理论上应该溢出,但因为系统 BUG ,造成实际取了真实的最小值,变量 e 运行后再次溢出。

注意,如果修改了 test.c 的代码,需要重新编译文件(指令:update /cmds/test)或者重启系统(指令:shutdown)才能生效。

示例代码中的 printf() 函数是LPC语言的 efun,可以理解为类似C语言的库函数(Library Function),因为LPC是从C语言衍生的,语法结构和C语言基本一样,但是C语言的库函数在LPC中不存在,千万不要直接把C语言中的函数在LPMUD开发中直接用,LPC语言中有很多和C语言同名且功能相同或相似的函数,如 printf(),但也有很多和C语言同名但功能不太一样的函数,如 sizeof(),还有更多C语言中没有的函数,如 this_player(),这些独有的函数让LPC开发网络游戏变的更为便捷,关于函数,后续章节会重点介绍。

为方便学习,这里先补充一下格式化输出函数 printf()的用法,在LPC语言中的用法和C语言中的同名函数基本一样,只是格式控制修饰符和数据类型有一些差异。printf() 格式控制符的完整形式如下:

%[flag][width][.precision]type

[ ] 表示此处的内容可有可无,是可以省略的。

和C语言相比,标志控制符(flag)增加了“|”(列居中对齐)、“=”(字符串纵列模式)、“'X'”(使用指定字符填充空位,X代表任意字符)和 “@”(指明参数为数组);修改了“#”的作用为字符串输出为表格模式。

输出类型(type)只有 "c"、"s"、"d/i"、"f"、"o"、"x/X",作用和C语言一致,同时新增了"O"表示LPC语言数据类型(即可输出LPC语言的任何类型),关于 printf函数 的说明文档可看这里:printf/sprintf

这里需要特别说明的是,LPC语言中没有字符型(char),但是在输出中可以把整型输出为字符,而且和C语言一样,可以直接把字符赋值给整型变量。C语言中的整数除了可以使用十进制,还可以使用二进制、八进制和十六进制,但是在LPC语言中,整数只能用十进制和十六进制赋值,可以用八进制输出,但不能用八进制赋值,而且即不能用二进制赋值也无法用二进制输出。

修改 test.c 代码如下,并 update /cmds/test

int main(object me, string arg)
{
    int a = 8, b = 'a', c = 0xF;

    printf("a = %o b = %d c = %d\n", a, b, c);

    return 1;
}

输出结果为:

a = 10 b = 97 c = 15

如果修改代码使用八进制赋值会发现其实还是十进制,而用二进制赋值的话,代码编译报错。

2. 单精度浮点型(float)

在LPC语言中,小数只有 float 类型,但是实际和C语言中的 double 类型一样,取值范围为 ±1.7E-308 和 ±1.7E308 之间。

和C语言不同的是,LPC语言中的浮点数只能用十进制形式表示,不可以使用指数形式,如果使用指数形式赋值会报错。另外,因为LPC语言中只有一种小数类型,所以,也就没有C语言中的数字加后缀L或F指明类型了。

在 fluffos 中,也定义了二个宏表示特定的浮点数,MAX_FLOAT 表示浮点数的最大值,但是 MIN_FLOAT 却是表示 0.00000,这很奇怪,不知道是 BUG,还是特意这样设定的。另外,在不同的操作系统下,浮点数的最大值和最小值是不一样的。

test.c 中使用以下代码试试看,会输出一个大到你数不出来的数字(整数部分309位)。

int main(object me, string arg)
{
    float f = MAX_FLOAT;
    printf("f = %f\n",f);

    return 1;
}

3. 字符串类型string)

和C语言差别比较大的一种数据类型,我们知道,C语言中的字符串类型实际上是字符数组,可以使用以下几种方式赋值:

#include <stdio.h>

int main(int argc, char const *argv[])
{
    char str1[] = {"mud.ren"};
    char str2[] = "mud.wiki";
    char *str = "www.mud.ren";

    printf("str1 = %s\nstr2 = %s\nstr = %s\n", str1, str2, str);
    return 0;
}

在LPC语言中,没有字符类型,无法使用这种方式赋值字符串,但是单独增加了字符串类型(string),可以直接赋值并使用。

int main(object me, string arg)
{
    string s = "www.mud.ren";
    printf("s = %s\n",s);

    return 1;
}

在LPC语言中,对字符串取子字符串的操作很别致而灵活,使用子字符串操作符,形式是:

str[n1..n2];

正整数代表从左开始,负整数代表从右开始,如果数值超过字符串的长度,视为字符串的长度。如果二个数值相等(str[n1..n1]),则传回字符串的第 n1 个字符。如果二个数值都超过字符串的长度,或者第一个数字所指的位置在第二个数字所指位置之后,会传回空字符串“”。
测试如下代码:

int main(object me, string arg)
{
    string s = "www.mud.ren";

    printf("s = %s\n",s);
    printf("s[4..4] = %s\n",s[4..4]);
    printf("s[4..6] = %s\n",s[4..6]);
    printf("s[0..20] = %s\n",s[0..20]);
    printf("s[20..30] = %s\n",s[20..30]);
    printf("s[1..0] = %s\n",s[1..0]);

    return 1;
}

输出结果:

s = www.mud.ren
s[4..4] = m
s[4..6] = mud
s[0..20] = www.mud.ren
s[20..30] =
s[1..0] =

4. 数组类型(array)

数组类型,LPC语言和C语言的差别还是比较大的,在C语言中数组定义方式为:

dataType  arrayName[length];

并且可以使用指针操作数组。例如:

#include <stdio.h>

int main(int argc, char const *argv[])
{
    int arr[] = {1, 2, 3, 4};
    int *p = arr;
    printf("arr[0] = %d\n", *p);
    return 0;
}

而在LPC语言中,数组用 ({}) 表示,并且使用类似指针的方式赋值,另外还有使用 外部函数 allocate() 初始化的方式。具体定义数组的方式如下:

dataType *arrayName;

我们继续测试如下代码:

int main(object me, string arg)
{
    string *str = ({"www", "mud", "ren"});
    int *arr = allocate(1 + random(9), (: $1 :));

    printf("str = %@-4s\n", str);
    printf("str[0] = %s, str[1] = %s, str[2] = %s\n", str[0], str[1], str[2]);
    printf("arr = %@','-2d\n", arr);

    return 1;
}

数组严格上说不是一种数据类型,只是一种数据集合,关于数组的使用,后续章节会详细讲解,这里先了解LPC语言中数组定义的方式。以上代码中第二种定义中使用了 random() 外部函数,所以使用 test 测试时每次输出是随机的。

5. 结构体类型(class)

结构体本质上也不是一种数据类型,而是一种数据集合,在C语言中数组是一组具有相同类型的数据的集合,而结构体用来存放一组不同类型的数据,但是在LPC语言中完全可以使用混合类型数组来实现存放不同类型的数据,或用使用更灵活的映射类型,所以结构体基本没什么大用,这里只做简单的介绍。

在C语言中的结构体类型关键字是 struct,LPC语言中,把关键词改成 class 了,结构体变量的定义方法和C语言有一点不一样的地方是C语言中结构体定义时 } 后面必须有 分号(;),而LPC语言中不需要,另外LPC语言中结构体赋值取值只能使用 ->

这里给一个具体的示例:

class example {
    string name;
    int age;
    string *lover;
}

int main(object me, string arg)
{
    // 变量
    class example instance = new(class example);
    // 赋值
    instance->age = 24;
    instance->name = "Ivy";
    instance->lover = ({"Alice", "Vivian", "Jessica"});
    // 取值
    printf("name : %s,age : %d, lover : %@-7s\n", instance->name, instance->age, instance->lover);
    return 1;
}

因为结构体类型在LPC语言中的定义和声明的方法不太一样,所以推荐使用 class 关键字,其实 struct 关键字也可以用,以上代码中 class 改成 struct 也可以,甚至混用也没错。

相关文章

  • LPC语言基本变量类型

    本文节选自本人写作的《 LPC 语言基础教程:从零学习游戏开发》第二章第一节。 第一节 LPC语言基本变量类型 L...

  • 静态语言和动态语言的区别

    基本概念 静态语言(强类型语言) 静态语言是在编译时变量的数据类型即可确定的语言,多数静态类型语言要求在使用变量之...

  • 数据类型

    Lua 数据类型 lua是动态类型语言(定义变量时不用指定变量类型) lua有8个基本类型nil、boolean、...

  • IT男的基础之路

    静态语言和动态语言 基本概念 静态语言(强类型语言) 静态语言是在编译时变量的数据类型即可确定的语言,多数静态类型...

  • 变量、作用域和内存问题

    javascript的变量和其他语言的变量有很大区别。 基本类型和引用类型的值 ECMAScript变量可能包含两...

  • go语言学习(2)--变量与常量

    任何编程语言都有变量,下面来学一学 go 的变量与其他语言有什么异同 go变量的基本类型 bool,string ...

  • JavaScript学习之路-变量

    一、变量 1.基本类型和引用类型 Javascript中的变量与其他编程语言中变量,也是有一定区别的,定义变量的时...

  • Javascript基本数据类型

    JavaScript 是一种弱类型语言 基本数据类型 基本类型是按值访问 Undefined使用var 声明变量但...

  • 我们一起学习GO语言 02

    接下来我们进入Go语言的基本语法与使用-变量 Go语言中标准声明变量的格式:var 变量名称 变量类型 例如-01...

  • Java - 变量、常量、作用域

    变量 变量:就是可以变化的量!Java是一种强类型的语言,每个变量都必须声明其类型。Java变量是程序中最基本的储...

网友评论

    本文标题:LPC语言基本变量类型

    本文链接:https://www.haomeiwen.com/subject/urqtnqtx.html