当前位置: 代码迷 >> 综合 >> 数蚕内存数据库查询语言规范
  详细解决方案

数蚕内存数据库查询语言规范

热度:76   发布时间:2024-02-26 19:59:29.0


数蚕内存数据库支持的最小操作单位为表,即不存在库概念;数蚕内存数据库基于列式存储,支持C++基础数据结构类型,包括整型、浮点型、字符串型。

数蚕内存数据库任意字段隐含一个基于平衡树的索引,详见create语句,sql语句中save和load语句支持表的保存与加载。
说明:数蚕内存数据库查询语言(以下简写为sql),类似标准查询语言(以下简写为SQL),基础语法结构兼容,整体处理流程不兼容SQL。

支持sql子查询、多表查询
支持字符模糊匹配和正则表达式匹配
支持完整的utf8字符编码(且唯一的)
良好的C语言接口操作形式

sql查询流程
内存实际存储是列式存储

存储方式
数蚕数据库数据处理流程如下:

where语句内容必为使用索引(此处不同于标准SQL语句)的检索条件,并应用条件过滤数据行。

行信息取出列内容并进行表达式计算,生出数据集。


数据集可以进行横向纵向(join/union)两种扩展,扩展为更大单一数据集。


单一集进行排序、过滤、分组聚合、投影、重命名和重计算几种后置运算操作。


排序


过滤有以下五种操作:

行内过滤


行间过滤,复杂度n*n


行邻过滤


行范围过滤


存在/子查询过滤


分组聚合


投影


重命名


重计算


sql基础规范
本文用于快速指导写出简单有效的数蚕数据库sql语句。
sql语句由DDL、DML组成,其中DDL由 select、 insert、 delete、 update、 rows_of、 cols_of、 fields_of、 show tables等组成;DML由 create、 alter、 drop、 save、 load、 exec等组成。
每一个sql语句非常数表达式或注释内容可接任意多个空白或注释字符,空白字符为0x09到0x0c(注意空白字符不包含0x0d,这意味着sql语句执行行尾默认为unix格式)或0x20的ASCII字符。
所有sql语句大小写严格区分,字符编码为唯一编码UTF-8。
每一个sql语句结束符为";",结束符在不影响语句解析时可以省略。

单行注释
#这是一个注释
//这是一个注释
--这是一个注释
多行注释
/*这是一
个注释
*/

(*这是一
个注释
*)
整数
0                      //有符号或无符号整数
1                      //省略符号整数
100                    //省略符号整数
+1                     //有符号整数
-100                   //有符号整数
-1000                  //有符号整数
+0b000                 //有符号二进制整数
-0xa0b3                //有符号十六进制整数
0xA0cD                 //无符号大小写混写十六进制整数
-847u2                 //有符号两字节长整数
56u1                   //无符号一字节长整数
0x0au1                 //无符号十六进制一字节整数
浮点数
+0.                    //无小数部分正浮点数
-0.01                  //仅小数部分负浮点数
-100.0                 //仅整数部分负浮点数
-100e20                //仅整数及正指数部分负浮点数
1.25E-32               //小数及负指数部分正浮点数
1.25E+20               //小数及正指数部分正浮点数
1.00E20f               //严格制定四字节浮点数
1.00E20d               //严格制定八字节浮点数
字符串
"a和中文bc"                            //包含中英文的有效字符串(UTF-8编码)
"ab和中文c\"\'\\\a\b\f\n\r\t\v"        //包含控制转义的有效字符串
"ab和中文c\x0a\x0001\uaabb\Uaabbccdd"  //包含十六进制转义和Unicode转义的有效字符串
@"aabbcc(018d7##@!@^_""AA6)aabbcc"    //以aabbcc为分割的原始字符串
表达式
表达式使用C语言表达式基础结构,保留对应运算符号优先级

id                           //域表达式表示对应字段值
(id)                         //括号表达式表示优先括号内容求值
id+10                        //加性表达式表示域字段与常数值10的和
id+max(grade)                //加性表达式表示域字段与grade域的最大值之和
id*sin(id)                   //积性表达式表示id域与id域的sin值之积
id << 10                     //移位表达式表示id域左移10位的值
id&&sin(id)>0                //逻辑与表达式表示id和sin(id)>0的逻辑与结果
id/sin(id)                   //积性表达式表示id与sin(id)之商
id&min(id)                   //位与表达式表示id与min(id)位与结果
id!=0||id==10                //逻辑或表达式表示id不等于0与id等于10的逻辑或结果

表达式类型转换及函数处理遵循以下原则
若数据类型可依据C++语言隐式转换为目标类型,则依C++隐式转换为目标类型。
函数处理过程为:若函数参数为字段,则函数作用于字段每一行的值,若函数参数为常数值,则使用常数值作为函数参数,若两参数
行数不相等,则使用较长行数作为输出结果,不足的较短参数使用最后一位连续填充至等长。
可用于表达式中函数
函数后为功能解释及使用示例

类型转换函数
x2i08                 //任意数据类型转换为一字节有符号整数          x2i08(type), x2i08(2.0)
x2i16                 //任意数据类型转换为两字节有符号整数          x2i16(type), x2i16(2.0)
x2i32                 //任意数据类型转换为四字节有符号整数          x2i32(type), x2i32(2.0)
x2i64                 //任意数据类型转换为八字节有符号整数          x2i64(type), x2i64(2.0)
x2u08                 //任意数据类型转换为一字节无符号整数          x2u08(type), x2u08(2.0)
x2u16                 //任意数据类型转换为两字节无符号整数          x2u16(type), x2u16(2.0)
x2u32                 //任意数据类型转换为四字节无符号整数          x2u32(type), x2u32(2.0)
x2u64                 //任意数据类型转换为八字节无符号整数          x2u64(type), x2u64(2.0)
x2flt                 //任意数据类型转换为四字节浮点数             x2flt(id), x2flt(10)
x2dbl                 //任意数据类型转换为八字节浮点数             x2dbl(id), x2dbl(10)
x2str                 //任意数据类型转换为字符串                  x2str(id), x2str(10)

聚集函数
sum                   //求某一列之和                          sum(id), sum(1.0)
product               //求某一列积                            product(id), product(1.0)
min                   //求某一列最小值                         min(id), min(1.0)
max                   //求某一列最大值                         max(id), max(1.0)
avg                   //求某一列均值                           avg(id), avg(1.0)
count                 //求某一列总数                           count(id), count(1.0)

范围函数
first                 //取某一列第一个元素                      first(id)
last                  //取某一列最后一个元素                    last(id)
first_k               //取某一列前k个元素                       first_k(id,10)
last_k                //取某一列最后k个元素                     last_k(id,20)

字符串函数
lcase                 //转换字符串为小写                       lcase("Abd")
ucase                 //转换字符串为大写                       ucase("abc")
concat                //连接两个字符串                         concat("abc","012")
length                //求字符串长度                           length("NAME")
substr                //取字符串从索引起始至固定数目的子字符串      substr(name, 1, 4)
replace               //替换字符串的子串为新的串                 replace(name, 2, 4, "abc")
trim_l                //移出字符串左边连续空格                   trim_l(name)
trim_r                //移出字符串右边连续空格                   trim_r(name)
trim                  //移出字符串两边连续空格                   trim(name)
reg_match             //正则表达式匹配(使用ECMA-262(2011)标准)   reg_match(id,".*[0-9]+.*")
fuzzy_match           //匹配一半字符差异的模糊检索                fuzzy_match(id,"what")

数学函数
abs                   //求数值的绝对值                         abs(value)
ceil                  //求数值的不小于给定值的最小整数            ceil(value)
floor                 //求数值的不大于给定值的最大整数            floor(value)
round                 //求数值的四舍五入值                      round(3.4)
exp                   //求数值的e的定幂                        exp(value)
pow                   //求数值的幂                            pow(id,2.0)
pi                    //常数值Π                               pi()
sqrt                  //求数值的开平方                         sqrt(value)
log                   //求数值的自然对数                       log(value)
sin                   //求数值的正弦值                         sin(value)
cos                   //求数值的余弦值                         cos(value)
tan                   //求数值的正切值                         tan(value)
asin                  //求数值的反正弦值                       asin(value)
acos                  //求数值的反余弦值                       acos(value)
atan                  //求数值的反正切值                       atan(value)
e                     //数学常数e                             e()

内部函数
raw2hex               //内存十六进制显示                       raw2hex(id)
row_id                //输出行号                             row_id()
id                    //输出内部id                           id()

统计函数
var                   //输出方差                             var(id)
stddev                //标准差                               stddev(id)

序列函数
seq                   //输出序列0到n        seq(10), seq(count(id)), seq(3)*3
rand                  //输出随机数          rand()
constants             //输出n个常数         constants(1,10), constants("sss",10)
where条件允许使用关系运算、范围运算、in运算及逻辑运算
id>=10                           //大于等于逻辑运算
id>=all (select id from t2)      //大于等于子查询全部结果的逻辑运算
id==any (select id from t2)      //等于子查询任意结果的逻辑运算
id==any (1,3,5,7)                //等于集合的任意结果的逻辑运算
id==10                           //等于逻辑运算
id!=10                           //不等于逻辑运算
id>=10&&id<=20                   //关系运算之间的逻辑与运算
id>=10||(id < 5&& id > 1)        //关系运算之间的逻辑或运算
10 <= id <= 20                   //关系运算的小于等于、小于等于运算
10 < id <= 20                    //关系运算的小于、小于等于运算

first                            //范围运算的第一个
last                             //范围运算的最后一个
first 100                        //范围运算的前100个
last 100                         //范围运算的后100个
range 10 100                     //范围运算的第10到100个
nth 10                           //范围运算的第10小的数
id max                           //值范围运算的最大的一个
id min                           //值范围运算的最小的一个
id max 100                       //值范围运算的最大的前100个
id min 100                       //值范围运算的最小的前100个 

id in (1,2,3,4,7)                //in运算取id为1,2,3,4,7的id
id in (select id from t2);       //取出id属于子表达式中的结果
id not in (select id from t2);   //取出id不属于子表达式中的结果


注意以下为无效的where条件
10 < id                          //字段名id应该放在前面
select语句
select * from table1;
//从table1选出所有字段

select id from tab2;
//从tab2选出id字段

select id /sin(id) from tab2 where id < 10;
//从tab2种选出id小于10的id数据并求id除以sin(id)的值

select max(id) from tab2 where id < 10&&id > 3;
//从tab2中选出大于3小于10的最大id

select id << 10 from tab2 where id!=3
//从tab2中选出id不等于3的id并左移10位

select sin(id),name into t2 from t1 where id < 10;
//从t1中选出id小于10以sin(id),name为列插入t2

select * from t1 where id in (select id2 from t2 where id2 > 10);
//从t1中选出当id在t2中当id2大于10的id2中t1的全部

select * from t1 where id < 10 order by id, name asc;
//从t1中选出当id小于10的全部后按id和name排字典升序

select * from t1 where id < 10 group sum(id) by name;
//从t1中选出当id小于10的全部后用name来分组sum(id)

select * from t1 where id < 10 filter all_each on distinct;
//从t1中选出当id小于10的全部后过滤所有行去重

select * from t1 where id < 10 filter all_each on id==id && name==name;
//从t1中选出当id小于10的全部后过滤所有行id相同和name相同的数据

select * from t1 where id < 10 filter adj on id>id && name==name;
//从t1中选出当id小于10的全部后过滤行邻id大于上一个id和name相同的数据

select * from t1 where id < 10 filter inner on id==name;
//从t1中选出当id小于10的全部后过滤行内id和name相同的数据

select * from t1 where id < 10 filter first;
//从t1中选出当id小于10的全部后过滤保留第一行

select * from t1 where id < 10 filter first 30;
//从t1中选出当id小于10的全部后过滤保留前30行

select * from t1 where id < 10 filter range 30 40;
//从t1中选出当id小于10过滤保留30行到40行范围内的数据

select * from t1 where id < 10 filter range except 30 40;
//从t1中选出当id小于10的全部后过滤保留除前30行和后40行以外的数据

select id1,name from t1 where id < 10 filter exists (select id from t2 where id==id1);
//从t1中选出当id小于10的并且在t2中存在的id1和name

select id as nid,name from t1 where id < 10 filter not exists (select id from t2 where id==nid);
//从t1中选出当id小于10的并且在t2中不存在id等于nid的nid和name

select * from t1 where id < 10 recompute id=id+10;
//从t1中选出当id小于10的全部后重计算id等于id加10

select * from t1 where id < 10 recompute id+=10,name=x2str(id);
//从t1中选出当id小于10的全部后重计算列id等于id加10,name等于转换成字符串的id

select * from t1 where id < 10 project except id;
//从t1中选出当id小于10的全部后投影保留除id以外的列数据

select * from t1 where id < 10 project id;
//从t1中选出当id小于10的全部后投影保留列id

select * from t1 where id < 10 rename id newid;
//从t1中选出当id小于10的全部后重命名id为newid

select * from t1 where id < 10 project id filter range 30 40 group sum(id) by id order by id rand rename id newid;
//从t1中选出当id小于10的全部后投影id,过滤30到40范围内的数据,用id来分组sum(id),按id随机排序,重命名id为newid

select * from t1 where id < 10 join select * from t2 where id < 10 on id==id;
//从t1中选出当id小于10的全部后横向扩展从t2中选出当id小于10在id等于id时的全部

select sin(seq(count(id))+1), id, name from t1 where id < 10 union select * from t2 where id < 10;
//从t1中选出当id小于10的sin(seq(count(id))+1), id, name纵向扩展从t2中选出id小于10的全部

select sin(id) as sinid,id from t1 where id < 10 filter inner on sinid < id;
//从t1中选出当id小于10的sin(id)作为sinid和id过滤保留行内sinid小于id的数据
insert语句
insert into tab1 (name,id) values("张三",100);                      //单条插入
insert into tab2 (val,type)values(1.00,1)(2.00,2)(3.00,3);          //多条插入
insert into t2 (id,name) select id,name from t1;                    //插入子查询结果
insert into t2 (id,name) select seq(10)+1,"name"+x2str(seq(10)+1);  //插入自定义数据

注意数蚕内存数据库不支持null字段,所以insert必须为每一字段指定值
delete语句
delete from tab1 where id<10;            //从tab1中删除id小于10的所有数据
update语句
update tab1 set name="张三",id=10 where id==5;
//更新tab1中id等于5的name字段为张三id为10
create语句
create table tab1 (id u08 (false, false));
//创建表tab1,初始字段为id类型为一字节无符号整型,不允许重复

create table tab1 (val float(),name string(true));
//创建表tab1,初始字段val为浮点型不允许重复不允许自增,字段name为字符串型且允许重复

注意目前字段第二参数为保留参数,实际使用无效果
alter语句
alter table tab1 add id u08 (false, false);      //tab1中增加id字段
alter table tab1 modify id u08 (false, false);   //tab1中修改id字段类型,修改会清空之前字段数据,请备份
alter table tab1 rename id newid;                //tab1中重命名id字段为newid
alter table tab1 drop id;                        //tab1中删除id字段
drop语句
drop table tab1         //删除表tab1
truncate语句
truncate table t1;      //快速清空t1并保留数据结构
save语句
save tab1               //保存表tab1,保存的文件名和表名相同
load语句
load tab1               //加载表tab1,从文件中加载表tab1到数据中
字段名
abc
abc0123
ABC_abc
[有效非@字符串(见字符串)]
表名
abc
abc0123
ABC_abc
[有效非@字符串(见字符串)]
rows_of
rows_of tab1            //获取tab1的行数
cols_of
cols_of tab1            //获取tab1的列数
fields_of
fields_of tab1          //获取tab1的字段名
show tables
show tables             //获取数据库中的所有表名
exec
exec "data.sql"         //执行sql文件的所有语句


更多说明

  相关解决方案