用户:LynChern/Sandbox:修订间差异
更多操作
无编辑摘要 |
|||
| (未显示2个用户的78个中间版本) | |||
| 第1行: | 第1行: | ||
===表白=== | |||
我爱你[[用户:DGCK81LNN|LNN]]。千言万语汇集成简单表述,但我知道这是不够的。我不知道我能给你什么,但你填满了我(各种意义上)。你击碎了我为掩耳盗铃而筑起的高墙,温暖了我的心灵,让我感受到前所未有的关心与爱。我真希望能与你白头偕老。 | |||
===任务=== | |||
这是任务,要在此处的编辑工作: | |||
* 设计基本的语法 | |||
* 完成分支模块的书写 | |||
===本文尚未完工!=== | |||
A | 该语言当前处于构想阶段,有较多内容还未完全确立。目前主要以概念形式表达,具体的语法正在设计。 | ||
目前本文的书写方法有很多留空,这并不代表未来不会有具体的内容。 | |||
===本文格式=== | |||
> 代表注释。在本文最终完工时,所有注释都会被移除。 | |||
当注释被使用时,代表本段内容很可能在未来作出更改。 | |||
=简介= | |||
xxx语是一门高级编程语言,声明式语言 | |||
> 是的,我们连名字都未想好 | |||
==特点== | |||
==代码预览== | |||
===[[Hello World]]=== | |||
我是代码 | |||
===[[99 bottles of beer]]=== | |||
我是代码 | |||
===图灵完备证明=== | |||
该代码可以模拟一个[[]],证明了本语言是图灵完备的。 | |||
> 这个章节不可能叫图灵完备证明,届时会更名为图灵机的名字。 | |||
我是代码 | |||
=运行xxx语程序= | |||
要运行使用xxx语编写的程序,预期的用途是将源代码作为编译器的输入,从而被编译成可执行的目标语言的代码。 | |||
==Python编译器== | |||
将Python视为机器码的编译器。 | |||
<nowiki>[[解释器资源地址|Python实现]]</nowiki> | |||
> 等待开发计划 | |||
==[[WhatLang]]编译器== | |||
将WhatLang视为机器码的编译器。 | |||
<nowiki>[[解释器资源地址|Python实现]]</nowiki> | |||
> 等待开发计划 | |||
==[[Bootstrapping]]== | |||
使用xxx语表达编译器程序不是该语言的强项,实现有一定难度。在一段时间内,语言的设计者认为没有必要开发。 | |||
=基本要素= | |||
让我们看一段xxx语[[#代码预览|代码]]。 | |||
xxx语的代码可使用的字符包含了:所有ASCII可见字符(包含空格)及《通用汉字规范表》中的所有汉字。 | |||
未指定字符所使用的编码。目前几个有效的编译器都能接受以UTF-8为的编码的纯文本文件作为源代码文件。理论上允许使用上述字符集以外的字符作为代码的一部分,但未处理任何特殊情况,可能发生未知的错误。 | |||
xxx语的代码完全由以下这些要素构成: | |||
* 关键字 | |||
* 标识符 | |||
* 字面量 | |||
xxx语的关键字包含了在其他语言中通常被称为运算符与结构符的词元。 | |||
xxx语的代码是大小写敏感的,这意味着<code>apple</code>和<code>Apple</code>不是同一个词元。 | |||
xxx语对缩进不敏感。 | |||
> 目前还未设计如何区分关键字与标识符。可能会像[[wenyan|文言]]一样标识符有统一的特殊的格式,也可能像Python一样非关键字就是标识符。 | |||
==xxx语标识符== | |||
标识符是用来标识变量、函数、类、模块,或任何其他用户自定义项目的名称。 | |||
xxx语的标识符的特点在于: | |||
* 第一点 | |||
* 第二点 | |||
* 第三点 | |||
* ... | |||
> 额,我没设计好 | |||
==xxx语关键字== | |||
> 这一段好像有点问题,因为这个语言可能没有关键字这样的概念 | |||
下面列出了xxx语中的关键字。关键字承担着赋予代码明确语义的重要能力,是语言中的核心词元。您不能将其作为常量、变量、类或任何标识符的名称。 | |||
这些词元的具体作用会在下文逐步揭示。 | |||
{| class="wikitable" | |||
| entry a || entry b || entry c | |||
|- | |||
| entry a || entry b || entry c | |||
|} | |||
下面列出了xxx语中的保留字。保留字是指在语言的发展中为未来可能会添加的新特性或语法结构而预先留出的词元。它们目前没有实际的语义功能,但为了保证代码在未来版本中的兼容性,您同样不能将保留字作为常量、变量、类或任何标识符的名称。 | |||
{| class="wikitable" | |||
| entry a || entry b || entry c | |||
|- | |||
| entry a || entry b || entry c | |||
|} | |||
==xxx语字面量== | |||
> todo | |||
===转义符=== | |||
=数据类型= | |||
xxx语中有多种数据类型 | |||
xxx语是强类型的,它不支持自动类型转换。如果要转换类型,必须通过调用标准库函数等方法显式地将数据进行类型转换。 | |||
==原子类型== | |||
===一、整型=== | |||
xxx语实际上把整数存在你的计算机中的浮点寄存器中,所以实际上被当作浮点数看待。 | |||
int | |||
bool | |||
char | |||
enum | |||
===二、浮点=== | |||
float | |||
==结构类型== | |||
===三、数组=== | |||
arrary | |||
===四、类=== | |||
对象是类的实例 | |||
> todo | |||
=声明与赋值= | |||
声明是告诉编译器,应该以何种方式读取或写入数据,并为存储数据做准备,这个动作被称为分配内存地址。赋值,是将具体的内容填充到声明时已经分配好的内存地址。在声明时,还需要设置标识符,这是称呼这份数据的名字;在赋值后,就可以通过直接使用标识符,指代其对应的数据。 | |||
声明与赋值缺一不可,一个标识符只有在同时经历了声明和赋值之后,才能在代码中被正常使用。 | |||
整数 杯子 的值为 3 | |||
在这行代码中,<code>整数</code>指明了数据类型,<code>杯子</code>是具体的标识符,而<code>3</code>则是赋予该标识符的数据。 | |||
在声明时,如果不添加额外的关键字,那么在同一代码段内,您不能在下文再次声明或赋值同一个标识符,这样的数据也被称为常量。'''这意味着,xxx语默认声明的是常量。'''代码段的相关概念在后文介绍。 | |||
您可以先声明,然后再赋值。例如: | |||
整数 杯子 | |||
杯子 的值为 3 | |||
上述的两种声明的写法都被称为显式声明。 | |||
xxx语支持自动类型推断。这意味着,您可以在不显式指明数据类型的情况下,直接给一个标识符赋值。编译器会根据赋给它的具体内容,自动推断出该标识符的数据类型并完成内存分配。这种写法也被称为隐式声明。 | |||
例如: | |||
杯垫 的值为 5 | |||
在这行代码中,虽然我们没有写出代表整数类型的<code>整数</code>,但因为赋予的具体数据<code>5</code>是一个整数,编译器就会自动将<code>杯垫</code>推断为整数类型。在实际效果上,它与 <code>整数 杯垫 的值为 5</code> 是等价的。这种写法只是省去了指明数据类型,但不代表没有声明。这仍然是一行同时声明并赋值的代码。 | |||
=注释= | |||
在计算机语言中,注释是计算机语言的一个重要组成部分,用于在源代码中解释代码的作用,可以增强程序的可读性、可维护性。 | |||
xxx语注释是一种在xxx语程序中用于提供代码功能说明的文本。 | |||
注释不会被编译器包含在最终的可执行文件中,因此不会对程序的运行结果产生任何影响。 | |||
在程序中经常注释是良好的编程习惯,它们帮助程序员更容易地理解代码的用途和功能,并且在团队协作中非常有用。 | |||
xxx语没有行内注释与多行注释之分,其写法如下: | |||
我觉得 睡前来一杯牛奶很助眠。 | |||
或者 | |||
我想 睡前来一杯牛奶。 | |||
其中,<code>睡前来一杯牛奶很助眠</code>和<code>睡前来一杯牛奶</code>被称为注释的文本。<code>我觉得</code>和<code>我想</code>是用于标记注释开始的关键字,句号是用于标记注释结束的关键字。'''注释需要使用关键字'''是该语言的特色之一。 | |||
==语气词== | |||
语气词是xxx语中一些无意义的关键字,它也是一种注释,但不包含自定义文本的部分。这些关键字在现在没有意义,在未来也不会赋予任何意义。 | |||
{| class="wikitable" | |||
| entry a || entry b || entry c | |||
|- | |||
| entry a || entry b || entry c | |||
|} | |||
=基本表达式= | |||
表达式用于向机器描述您的意图。表达式由操作数和运算符组成。把表达式写在代码中合适的位置就会被执行,它会按照运算符的优先级依次计算。在每次运算中,运算符会对它所需要使用的操作数进行运算。每次运算都会消耗运算符和操作数,这意味着运算的结果将代替原本的运算符与操作数成为一个新的操作数。 | |||
先看一个例子: | |||
整数 杯子 的值为 5 加上 7 | |||
这条代码将<code>5 加上 7</code>的结果赋予到整数<code>杯子</code>中。 | |||
xxx语言具有丰富的运算符,'''同一个运算符还可能有多种不同的写法'''以适应不同的语气。使用纯符号运算符不需要空格,使用关键字运算符有空格,否则可能会被当作其他的普通标识符。 | |||
以下这些是最常使用的几个运算符。 | |||
==算数运算符== | |||
算数运算符是使用浮点或整型作为操作数运算的运算符,运算结果的类型与操作数相同,即没有自动类型转换。 | |||
{| class="wikitable" | |||
|- | |||
! 运算符 !! 描述 !! 例子 | |||
|- | |||
| <code>+</code> <code>加</code> <code>加上</code> || 加法 - 将两操作数相加 || <code>7+3</code>的输出结果为整数"10" | |||
|- | |||
| <code>-</code> <code>减</code> <code>减去</code> || 减法 - 将左边的操作数减去右边的操作数 || <code>7-3</code>的输出结果为整数"4" | |||
|- | |||
| <code>*</code> <code>乘</code> <code>乘以</code> || 乘法 - 将两操作数相乘 || <code>7*3</code>的输出结果为整数"21" | |||
|- | |||
| <code>/</code> <code>除以</code> || 除法 - 将左边的操作数除以右边的操作数,取小数<br/>操作数只能是浮点类型 || <code>7.0/3.0</code>的输出结果为浮点数<br/>"2.3333333333333333333333333333333" | |||
|- | |||
| <code>整除</code> || 整除 - 将左边的操作数除以右边的操作数,取商 || <code>7 整除 3</code>的输出结果为整数"2" | |||
|- | |||
| <code>模</code> || 取余 - 将左边的操作数除以右边的操作数,取余数 || <code>7 模 3</code>的输出结果为整数"1" | |||
|} | |||
==比较运算符== | |||
比较运算符是使用浮点或整型作为操作数的运算符,运算结果的类型是布尔类型。 | |||
{| class="wikitable" | |||
|- | |||
! 运算符 !! 描述 !! 例子 | |||
|- | |||
| <code>==</code> <code>等于</code> || 检查两个操作数的值是否相等,如果相等则为真 || <code>5+3</code>的输出结果为布尔值"8" | |||
|- | |||
| <code>!=</code> <code>不等于</code> || 检查两个操作数的值是否相等,如果不相等则为真 || <code>5-3</code>的输出结果为布尔值"2" | |||
|- | |||
| <code>></code> <code>大于</code> || 检查左操作数的值是否大于右操作数的值,如果是则为真 || <code>5*3</code>的输出结果为布尔值"15" | |||
|- | |||
| <code><</code> <code>小于</code> || 检查左操作数的值是否小于右操作数的值,如果是则为真 || <code>我是代码</code>的输出结果为布尔值"" | |||
|- | |||
| <code>>=</code> <code>不小于</code><br/><code>大于等于</code> || 检查左操作数的值是否大于或等于右操作数的值,如果是则为真 || <code>我是代码</code>的输出结果为布尔值"" | |||
|- | |||
| <code><=</code> <code>不大于</code><br/><code>小于等于</code> || 检查左操作数的值是否小于或等于右操作数的值,如果是则为真 || <code>我是代码</code>的输出结果为布尔值"" | |||
|} | |||
==逻辑运算符== | |||
逻辑运算符是使用布尔值作为操作数的运算符,运算结果的类型是布尔类型。 | |||
{| class="wikitable" | |||
|- | |||
! 运算符 !! 描述 !! 例子 | |||
|- | |||
| <code>并且</code> || 如果两个操作数都为真,则为真 || <code>我是代码</code>的输出结果为布尔值"" | |||
|- | |||
| <code>或者</code> || 如果两个操作数至少有一个为真,则为真 || <code>我是代码</code>的输出结果为布尔值"" | |||
|- | |||
| <code>不成立</code> || 如果操作数为真,则表达式为假;如果操作数为假,则表达式为真 || <code>我是代码</code>的输出结果为布尔值"" | |||
|} | |||
=代码块= | |||
代码块是xxx语的核心概念,也是该语言的特色之一。 | |||
代码块的写法如下: | |||
做 | |||
... | |||
这些事 | |||
上述代码中,"..."代表您可以在此处插入代码,例如: | |||
做 | |||
我是代码 | |||
我是代码 | |||
我是代码 | |||
这些事 | |||
可插入的代码数量不限。 | |||
注意看: | |||
A | |||
做 | |||
B | |||
... | |||
这些事 | |||
其中,B所在的位置,是这个代码块的'''内部''';A所在的位置,是这个代码块的'''外层'''。 | |||
代码块可以写在程序中,也可以写在任何可以插入代码的位置。代码块可以被写在代码块的内部,这被称为代码块的嵌套,例如: | |||
做 | |||
做 | |||
... | |||
这些事 | |||
... | |||
这些事 | |||
同样的,嵌套的层数不限。 | |||
==作用域== | |||
在标识符经历了声明后,在一定范围内相同的标识符可以指代相同的东西,这个范围被称作'''作用域'''。 | |||
在xxx语中,任何一个标识符一旦在程序中完成声明,它的作用域就是自声明位置开始,直至程序代码结束的全部文本剩余部分。 | |||
在下面这个代码块的内部,标识符""被赋予了""这个值。在""这行代码前,标识符""的含义未被定义,您不能在标识符被声明前使用它。 | |||
做 | |||
//""未定义 | |||
我是代码 | |||
//我所在的位置可以正常使用"" | |||
这些事 | |||
//我在上面这个代码块的外部,""未定义 | |||
最后一行注释由于在代码块的外层,不在标识符""的作用域内。 | |||
'''与其他语言不同的是,xxx语的代码块内部不能直接使用外层已声明的标识符。'''这意味着,声明的作用域不包含代码块。如下所示的这几行代码中,代码块的内部无法使用""。 | |||
我是代码 | |||
//我这里可以使用"" | |||
做 | |||
//而我这里""未定义 | |||
这些事 | |||
//我不在代码块里,不过我也能使用"" | |||
另一个例子: | |||
做 | |||
我是代码 | |||
//我这里可以使用"" | |||
做 | |||
//而我这里""未定义 | |||
这些事 | |||
//我与声明在同一个代码块里,所以我能使用"" | |||
这些事 | |||
上述这样的限制存在,为的是当您在编写代码时,您无需担心您的标识符已经被远在另一头的代码占用。大胆使用相同的关键字!本语言鼓励您使用相同的关键字写出易于理解的代码,专注于对您来说更重要的事。 | |||
此外,当您编辑一个xxx语源代码文件时,可以假想为您正在编辑一个代码块的内部,而这一整个文件就是那个代码块。 | |||
=引入= | |||
引入是使代码块与外界交互的重要代码。如果没有引入,由于代码块内部与外层隔离,代码块将无法发挥作用。 | |||
观察下面这段代码,注意""与""的值为何不同: | |||
我是代码 | |||
我是代码 | |||
做 | |||
我是代码 | |||
我是代码 | |||
//""被引入了,不能再次赋值,并且可以直接使用 | |||
我是代码 | |||
这些事 | |||
此时,外层标识符所指的数据与内部标识符所指的数据是同一个。 | |||
我是代码 | |||
这条指令就是引入,它代表把""引入到当前的代码块内。引入可以写在任意可以插入代码的位置,但是只有引入后的被引入的关键字才能使用。请尽量写在易于发现的地方,比如最开头或最结尾。 | |||
引入不仅能引入已赋值的标识符,还能引入已声明但未赋值的值: | |||
我是代码 | |||
我是代码 | |||
做 | |||
我是代码 | |||
我是代码 | |||
我是代码 | |||
这些事 | |||
//如果此时使用""是不行的,因为它没有被赋值 | |||
我是代码 | |||
这样,代码块的内部就可以和外层交互。'''这意味着引入可能导致的数据流向是双向的。'''它可以从外层把数据传入内部,也可以把数据从内部传给外层,同时外层不会被内部的标识符影响。尽管数据可以同时流入和流出,不过本语言仍然建议您为单一关键字计划明确的单方向数据流向,不要吝啬关键字的数量。 | |||
您也可以在引入时声明,这相当于在外层声明然后立即引入。赋值后,关键字在外层仍然可用。 | |||
做 | |||
我是代码 | |||
我是代码 | |||
这些事 | |||
我是代码 | |||
如果被引入的关键字之前就已经被占用了,您不能直接从外部引入它,这将导致编译器无法区分这两个不同的数据。您可以别名的方式引入。当以别名方式引入外层的一个关键字时,在这个代码块内,所有以别名作为关键字的使用或赋值最终都会影响到外层的那个关键字。如果没有额外的声明,代码块内部仍然无法使用外层关键字。并且即使声明了与外层相同的关键字,这两个关键字所指的数据也不会是同一个。 | |||
我是代码 | |||
我是代码 | |||
做 | |||
我是代码 | |||
//关键字""已经被声明占用 | |||
我是代码 | |||
我是代码 | |||
我是代码 | |||
//下面这是引入并别名 | |||
我是代码 | |||
我是代码 | |||
这些事 | |||
//在外层它仍然以原名获得数值 | |||
我是代码 | |||
以别名方式引入的关键字同样可以在引入时声明,以下是它的写法: | |||
我是代码 | |||
=分支= | |||
分支是您迈向流程控制的第一步! | |||
分支是一种流程控制,让您可以选择是否运行某条代码,或是选择运行多条代码之一。 | |||
一个分支由至少一个布尔类型的和与其对应数量对应的代码块组成。 | |||
选择分支结构: | |||
如果 我是代码 就 | |||
做 | |||
... | |||
这些事 | |||
不然就做 | |||
... | |||
这些事 | |||
如果<code>我是代码</code>的值为布尔值"真",就执行第一个代码块的内容,也就是A点部分的代码 | |||
=变量= | |||
> 本章内容未进行严格的论证,未确定具体的副作用 | |||
=循环= | |||
> 本章内容未进行严格的论证,未确定具体的副作用 | |||
=函数= | |||
==普通函数== | |||
> 普通函数的创建方法要卸载这儿 | |||
===调用普通函数=== | |||
===使用标准库中的函数=== | |||
==偏函数== | |||
> 本章内容未进行严格的论证,未确定具体的副作用 | |||
> 此处应该写如何把普通函数包装成偏函数对象 | |||
> 偏函数有一些实验性语法还未进行严格的论证,比如将偏函数作为一等公民的想法还在策划 | |||
===调用偏函数=== | |||
==返回值函数== | |||
> 本章内容未进行严格的论证,未确定具体的副作用 | |||
> 此处应该写如何将普通函数或偏函数包装成返回值函数,以及形成返回值函数的各种限制 | |||
> 此处会提到表达式中可以使用返回值函数 | |||
=面向对象= | |||
> 本章内容未进行严格的论证,未确定具体的副作用 | |||
概念: | |||
* 对象 | |||
* 类 | |||
* 结构 | |||
* 方法 | |||
继承 | |||
改写 | |||
==封包与肢解== | |||
封包是指将一组 | |||
肢解是一种特殊的导入,将对象中的某个函数及它的依赖加载到当前作用域中 | |||
=复杂表达式= | |||
==位运算符== | |||
位运算符是逻辑运算符的扩展。 | |||
=错误处理= | |||
=约定= | |||
该语言本身不具备某种数据结构,这是鼓励程序员自己实现。 | |||
不过,这里提出了一些约定配合标准库实现了一些其他语言常见的数据结构。 | |||
==带参数的排序== | |||
==字典== | |||
==递归== | |||
=里面有什么?= | |||
> todo | |||
本章介绍编译器在编译时内部会发生什么。 | |||
==内存布局== | |||
编译后的可执行文件在内存中的布局只包含'''代码区'''和'''栈区''',这是该语言的特色之一。 | |||
> 为并发添加分段栈的内容仍然在讨论阶段。以下内容仅供参考。 | |||
当您在源代码文件中添加了至少一行并发多线程代码时(即使用进程冷却锁),会引入一个额外的标准库。这会导致栈区变更为分段栈,这意味着它本质上是一个堆,由标准库自动进行内存管理。多线程会导致额外且不明显的内存与性能开销。 | |||
==影子栈== | |||
xxx语言刻意向程序员隐藏了生命周期的概念。 | |||
这为内存安全的特性保驾护航。 | |||
2026年6月3日 (三) 19:07的最新版本
表白
我爱你LNN。千言万语汇集成简单表述,但我知道这是不够的。我不知道我能给你什么,但你填满了我(各种意义上)。你击碎了我为掩耳盗铃而筑起的高墙,温暖了我的心灵,让我感受到前所未有的关心与爱。我真希望能与你白头偕老。
任务
这是任务,要在此处的编辑工作:
- 设计基本的语法
- 完成分支模块的书写
本文尚未完工!
该语言当前处于构想阶段,有较多内容还未完全确立。目前主要以概念形式表达,具体的语法正在设计。
目前本文的书写方法有很多留空,这并不代表未来不会有具体的内容。
本文格式
> 代表注释。在本文最终完工时,所有注释都会被移除。
当注释被使用时,代表本段内容很可能在未来作出更改。
简介
xxx语是一门高级编程语言,声明式语言
> 是的,我们连名字都未想好
特点
代码预览
我是代码
我是代码
图灵完备证明
该代码可以模拟一个[[]],证明了本语言是图灵完备的。
> 这个章节不可能叫图灵完备证明,届时会更名为图灵机的名字。
我是代码
运行xxx语程序
要运行使用xxx语编写的程序,预期的用途是将源代码作为编译器的输入,从而被编译成可执行的目标语言的代码。
Python编译器
将Python视为机器码的编译器。
[[解释器资源地址|Python实现]]
> 等待开发计划
WhatLang编译器
将WhatLang视为机器码的编译器。
[[解释器资源地址|Python实现]]
> 等待开发计划
使用xxx语表达编译器程序不是该语言的强项,实现有一定难度。在一段时间内,语言的设计者认为没有必要开发。
基本要素
让我们看一段xxx语代码。
xxx语的代码可使用的字符包含了:所有ASCII可见字符(包含空格)及《通用汉字规范表》中的所有汉字。
未指定字符所使用的编码。目前几个有效的编译器都能接受以UTF-8为的编码的纯文本文件作为源代码文件。理论上允许使用上述字符集以外的字符作为代码的一部分,但未处理任何特殊情况,可能发生未知的错误。
xxx语的代码完全由以下这些要素构成:
- 关键字
- 标识符
- 字面量
xxx语的关键字包含了在其他语言中通常被称为运算符与结构符的词元。
xxx语的代码是大小写敏感的,这意味着apple和Apple不是同一个词元。
xxx语对缩进不敏感。
> 目前还未设计如何区分关键字与标识符。可能会像文言一样标识符有统一的特殊的格式,也可能像Python一样非关键字就是标识符。
xxx语标识符
标识符是用来标识变量、函数、类、模块,或任何其他用户自定义项目的名称。
xxx语的标识符的特点在于:
- 第一点
- 第二点
- 第三点
- ...
> 额,我没设计好
xxx语关键字
> 这一段好像有点问题,因为这个语言可能没有关键字这样的概念
下面列出了xxx语中的关键字。关键字承担着赋予代码明确语义的重要能力,是语言中的核心词元。您不能将其作为常量、变量、类或任何标识符的名称。
这些词元的具体作用会在下文逐步揭示。
| entry a | entry b | entry c |
| entry a | entry b | entry c |
下面列出了xxx语中的保留字。保留字是指在语言的发展中为未来可能会添加的新特性或语法结构而预先留出的词元。它们目前没有实际的语义功能,但为了保证代码在未来版本中的兼容性,您同样不能将保留字作为常量、变量、类或任何标识符的名称。
| entry a | entry b | entry c |
| entry a | entry b | entry c |
xxx语字面量
> todo
转义符
数据类型
xxx语中有多种数据类型
xxx语是强类型的,它不支持自动类型转换。如果要转换类型,必须通过调用标准库函数等方法显式地将数据进行类型转换。
原子类型
一、整型
xxx语实际上把整数存在你的计算机中的浮点寄存器中,所以实际上被当作浮点数看待。 int bool char enum
二、浮点
float
结构类型
三、数组
arrary
四、类
对象是类的实例
> todo
声明与赋值
声明是告诉编译器,应该以何种方式读取或写入数据,并为存储数据做准备,这个动作被称为分配内存地址。赋值,是将具体的内容填充到声明时已经分配好的内存地址。在声明时,还需要设置标识符,这是称呼这份数据的名字;在赋值后,就可以通过直接使用标识符,指代其对应的数据。
声明与赋值缺一不可,一个标识符只有在同时经历了声明和赋值之后,才能在代码中被正常使用。
整数 杯子 的值为 3
在这行代码中,整数指明了数据类型,杯子是具体的标识符,而3则是赋予该标识符的数据。
在声明时,如果不添加额外的关键字,那么在同一代码段内,您不能在下文再次声明或赋值同一个标识符,这样的数据也被称为常量。这意味着,xxx语默认声明的是常量。代码段的相关概念在后文介绍。
您可以先声明,然后再赋值。例如:
整数 杯子 杯子 的值为 3
上述的两种声明的写法都被称为显式声明。
xxx语支持自动类型推断。这意味着,您可以在不显式指明数据类型的情况下,直接给一个标识符赋值。编译器会根据赋给它的具体内容,自动推断出该标识符的数据类型并完成内存分配。这种写法也被称为隐式声明。
例如:
杯垫 的值为 5
在这行代码中,虽然我们没有写出代表整数类型的整数,但因为赋予的具体数据5是一个整数,编译器就会自动将杯垫推断为整数类型。在实际效果上,它与 整数 杯垫 的值为 5 是等价的。这种写法只是省去了指明数据类型,但不代表没有声明。这仍然是一行同时声明并赋值的代码。
注释
在计算机语言中,注释是计算机语言的一个重要组成部分,用于在源代码中解释代码的作用,可以增强程序的可读性、可维护性。
xxx语注释是一种在xxx语程序中用于提供代码功能说明的文本。
注释不会被编译器包含在最终的可执行文件中,因此不会对程序的运行结果产生任何影响。
在程序中经常注释是良好的编程习惯,它们帮助程序员更容易地理解代码的用途和功能,并且在团队协作中非常有用。
xxx语没有行内注释与多行注释之分,其写法如下:
我觉得 睡前来一杯牛奶很助眠。
或者
我想 睡前来一杯牛奶。
其中,睡前来一杯牛奶很助眠和睡前来一杯牛奶被称为注释的文本。我觉得和我想是用于标记注释开始的关键字,句号是用于标记注释结束的关键字。注释需要使用关键字是该语言的特色之一。
语气词
语气词是xxx语中一些无意义的关键字,它也是一种注释,但不包含自定义文本的部分。这些关键字在现在没有意义,在未来也不会赋予任何意义。
| entry a | entry b | entry c |
| entry a | entry b | entry c |
基本表达式
表达式用于向机器描述您的意图。表达式由操作数和运算符组成。把表达式写在代码中合适的位置就会被执行,它会按照运算符的优先级依次计算。在每次运算中,运算符会对它所需要使用的操作数进行运算。每次运算都会消耗运算符和操作数,这意味着运算的结果将代替原本的运算符与操作数成为一个新的操作数。
先看一个例子:
整数 杯子 的值为 5 加上 7
这条代码将5 加上 7的结果赋予到整数杯子中。
xxx语言具有丰富的运算符,同一个运算符还可能有多种不同的写法以适应不同的语气。使用纯符号运算符不需要空格,使用关键字运算符有空格,否则可能会被当作其他的普通标识符。
以下这些是最常使用的几个运算符。
算数运算符
算数运算符是使用浮点或整型作为操作数运算的运算符,运算结果的类型与操作数相同,即没有自动类型转换。
| 运算符 | 描述 | 例子 |
|---|---|---|
+ 加 加上 |
加法 - 将两操作数相加 | 7+3的输出结果为整数"10"
|
- 减 减去 |
减法 - 将左边的操作数减去右边的操作数 | 7-3的输出结果为整数"4"
|
* 乘 乘以 |
乘法 - 将两操作数相乘 | 7*3的输出结果为整数"21"
|
/ 除以 |
除法 - 将左边的操作数除以右边的操作数,取小数 操作数只能是浮点类型 |
7.0/3.0的输出结果为浮点数"2.3333333333333333333333333333333" |
整除 |
整除 - 将左边的操作数除以右边的操作数,取商 | 7 整除 3的输出结果为整数"2"
|
模 |
取余 - 将左边的操作数除以右边的操作数,取余数 | 7 模 3的输出结果为整数"1"
|
比较运算符
比较运算符是使用浮点或整型作为操作数的运算符,运算结果的类型是布尔类型。
| 运算符 | 描述 | 例子 |
|---|---|---|
== 等于 |
检查两个操作数的值是否相等,如果相等则为真 | 5+3的输出结果为布尔值"8"
|
!= 不等于 |
检查两个操作数的值是否相等,如果不相等则为真 | 5-3的输出结果为布尔值"2"
|
> 大于 |
检查左操作数的值是否大于右操作数的值,如果是则为真 | 5*3的输出结果为布尔值"15"
|
< 小于 |
检查左操作数的值是否小于右操作数的值,如果是则为真 | 我是代码的输出结果为布尔值""
|
>= 不小于大于等于 |
检查左操作数的值是否大于或等于右操作数的值,如果是则为真 | 我是代码的输出结果为布尔值""
|
<= 不大于小于等于 |
检查左操作数的值是否小于或等于右操作数的值,如果是则为真 | 我是代码的输出结果为布尔值""
|
逻辑运算符
逻辑运算符是使用布尔值作为操作数的运算符,运算结果的类型是布尔类型。
| 运算符 | 描述 | 例子 |
|---|---|---|
并且 |
如果两个操作数都为真,则为真 | 我是代码的输出结果为布尔值""
|
或者 |
如果两个操作数至少有一个为真,则为真 | 我是代码的输出结果为布尔值""
|
不成立 |
如果操作数为真,则表达式为假;如果操作数为假,则表达式为真 | 我是代码的输出结果为布尔值""
|
代码块
代码块是xxx语的核心概念,也是该语言的特色之一。
代码块的写法如下:
做
...
这些事
上述代码中,"..."代表您可以在此处插入代码,例如:
做
我是代码
我是代码
我是代码
这些事
可插入的代码数量不限。
注意看:
A
做
B
...
这些事
其中,B所在的位置,是这个代码块的内部;A所在的位置,是这个代码块的外层。
代码块可以写在程序中,也可以写在任何可以插入代码的位置。代码块可以被写在代码块的内部,这被称为代码块的嵌套,例如:
做
做
...
这些事
...
这些事
同样的,嵌套的层数不限。
作用域
在标识符经历了声明后,在一定范围内相同的标识符可以指代相同的东西,这个范围被称作作用域。
在xxx语中,任何一个标识符一旦在程序中完成声明,它的作用域就是自声明位置开始,直至程序代码结束的全部文本剩余部分。
在下面这个代码块的内部,标识符""被赋予了""这个值。在""这行代码前,标识符""的含义未被定义,您不能在标识符被声明前使用它。
做
//""未定义
我是代码
//我所在的位置可以正常使用""
这些事
//我在上面这个代码块的外部,""未定义
最后一行注释由于在代码块的外层,不在标识符""的作用域内。
与其他语言不同的是,xxx语的代码块内部不能直接使用外层已声明的标识符。这意味着,声明的作用域不包含代码块。如下所示的这几行代码中,代码块的内部无法使用""。
我是代码
//我这里可以使用""
做
//而我这里""未定义
这些事
//我不在代码块里,不过我也能使用""
另一个例子:
做
我是代码
//我这里可以使用""
做
//而我这里""未定义
这些事
//我与声明在同一个代码块里,所以我能使用""
这些事
上述这样的限制存在,为的是当您在编写代码时,您无需担心您的标识符已经被远在另一头的代码占用。大胆使用相同的关键字!本语言鼓励您使用相同的关键字写出易于理解的代码,专注于对您来说更重要的事。
此外,当您编辑一个xxx语源代码文件时,可以假想为您正在编辑一个代码块的内部,而这一整个文件就是那个代码块。
引入
引入是使代码块与外界交互的重要代码。如果没有引入,由于代码块内部与外层隔离,代码块将无法发挥作用。
观察下面这段代码,注意""与""的值为何不同:
我是代码
我是代码
做
我是代码
我是代码
//""被引入了,不能再次赋值,并且可以直接使用
我是代码
这些事
此时,外层标识符所指的数据与内部标识符所指的数据是同一个。
我是代码
这条指令就是引入,它代表把""引入到当前的代码块内。引入可以写在任意可以插入代码的位置,但是只有引入后的被引入的关键字才能使用。请尽量写在易于发现的地方,比如最开头或最结尾。
引入不仅能引入已赋值的标识符,还能引入已声明但未赋值的值:
我是代码
我是代码
做
我是代码
我是代码
我是代码
这些事
//如果此时使用""是不行的,因为它没有被赋值
我是代码
这样,代码块的内部就可以和外层交互。这意味着引入可能导致的数据流向是双向的。它可以从外层把数据传入内部,也可以把数据从内部传给外层,同时外层不会被内部的标识符影响。尽管数据可以同时流入和流出,不过本语言仍然建议您为单一关键字计划明确的单方向数据流向,不要吝啬关键字的数量。
您也可以在引入时声明,这相当于在外层声明然后立即引入。赋值后,关键字在外层仍然可用。
做
我是代码
我是代码
这些事
我是代码
如果被引入的关键字之前就已经被占用了,您不能直接从外部引入它,这将导致编译器无法区分这两个不同的数据。您可以别名的方式引入。当以别名方式引入外层的一个关键字时,在这个代码块内,所有以别名作为关键字的使用或赋值最终都会影响到外层的那个关键字。如果没有额外的声明,代码块内部仍然无法使用外层关键字。并且即使声明了与外层相同的关键字,这两个关键字所指的数据也不会是同一个。
我是代码
我是代码
做
我是代码
//关键字""已经被声明占用
我是代码
我是代码
我是代码
//下面这是引入并别名
我是代码
我是代码
这些事
//在外层它仍然以原名获得数值
我是代码
以别名方式引入的关键字同样可以在引入时声明,以下是它的写法:
我是代码
分支
分支是您迈向流程控制的第一步!
分支是一种流程控制,让您可以选择是否运行某条代码,或是选择运行多条代码之一。
一个分支由至少一个布尔类型的和与其对应数量对应的代码块组成。
选择分支结构:
如果 我是代码 就
做
...
这些事
不然就做
...
这些事
如果我是代码的值为布尔值"真",就执行第一个代码块的内容,也就是A点部分的代码
变量
> 本章内容未进行严格的论证,未确定具体的副作用
循环
> 本章内容未进行严格的论证,未确定具体的副作用
函数
普通函数
> 普通函数的创建方法要卸载这儿
调用普通函数
使用标准库中的函数
偏函数
> 本章内容未进行严格的论证,未确定具体的副作用
> 此处应该写如何把普通函数包装成偏函数对象
> 偏函数有一些实验性语法还未进行严格的论证,比如将偏函数作为一等公民的想法还在策划
调用偏函数
返回值函数
> 本章内容未进行严格的论证,未确定具体的副作用
> 此处应该写如何将普通函数或偏函数包装成返回值函数,以及形成返回值函数的各种限制
> 此处会提到表达式中可以使用返回值函数
面向对象
> 本章内容未进行严格的论证,未确定具体的副作用
概念:
- 对象
- 类
- 结构
- 方法
继承 改写
封包与肢解
封包是指将一组
肢解是一种特殊的导入,将对象中的某个函数及它的依赖加载到当前作用域中
复杂表达式
位运算符
位运算符是逻辑运算符的扩展。
错误处理
约定
该语言本身不具备某种数据结构,这是鼓励程序员自己实现。
不过,这里提出了一些约定配合标准库实现了一些其他语言常见的数据结构。
带参数的排序
字典
递归
里面有什么?
> todo
本章介绍编译器在编译时内部会发生什么。
内存布局
编译后的可执行文件在内存中的布局只包含代码区和栈区,这是该语言的特色之一。
> 为并发添加分段栈的内容仍然在讨论阶段。以下内容仅供参考。
当您在源代码文件中添加了至少一行并发多线程代码时(即使用进程冷却锁),会引入一个额外的标准库。这会导致栈区变更为分段栈,这意味着它本质上是一个堆,由标准库自动进行内存管理。多线程会导致额外且不明显的内存与性能开销。
影子栈
xxx语言刻意向程序员隐藏了生命周期的概念。
这为内存安全的特性保驾护航。