数据库

基础 #

数据库类型
    关系型数据库
    模糊型数据库
        # 存放模糊数据,提供函数
        如模糊数,包括模糊区间数,模糊中心数,模糊集合数
        隶属函数
    统计数据库
        # 管理统计数据
        这类数据库包含有大量的数据记录,但其目的是向用户提供各种统计汇总信息,而不是提供单个记录的信息。
    网状数据库(层次数据库)
        # 处理以记录类型为结点的网状数据模型
        处理方法是将网状结构分解成若干棵二级树结构,称为系。
    演绎数据库
        # 指具有演绎推理能力
        实现
            数据库管理系统
            规则管理系统
        外延数据库
            将推理用的事实数据存放在数据库中
        内涵数据库
            用逻辑规则定义要导出的事实
        主要研究内容: 如何有效地计算逻辑规则推理。
            递归查询的优化
            规则的一致性维护

其它数据存储方式
    文件系统
        版本控制
    保存持久状态
        CQRS(command query responsibility segregation)
            查询(query)
            命令(command)
            领域模型(domain model)
            领域事件(domain event)
    对象数据库
趋势
    分布式new sql  # tidb
    Polyglot persistence (混合持久化)
        # 将对不同数据库的操作封装成服务

事务隔离级别
    读未提交(Read Uncommitted)  # 读其它事务未提交的数据
        现象
            不允许更新丢失
            允许脏读(dirty read)               # 事务中读到不存在数据, 是其它事务修改中的数据
        原理
            可同时读
            不同时写,多事务写
        实现
            排他写锁
    读提交(Read Committed)                    # 读其它事务提交的数据
        现象
            不允许脏读
            允许不可重复读(nonRepeatable read)   # 事务中前后查询不一致
        原理
            可同时读
            单事务写
        实现
            瞬间共享读锁
            排他写锁
    可重复读(Repeatable Read)                  # 读到的数据加锁,解决不可重复读问题
        现象
            不允许脏读
            不允许不可重复读
            允许幻读(phantom read)               # 事务中存在未生效行,是其它事务的插入或删除
        原理
            读到的数据(加锁)不写
            单事务写
        实现      # 读涉及范围加锁
            共享读锁
            排他写锁
    序列化(Serializable)       # 或叫串行化
        原理
            事务序列化执行
        实现
            读锁写锁互斥
事务特点(ACID)
    原子性(atomicity)          # 什么都做或都不做
    一致性(correspondence)     # 事务前后数据库状态一致, 事务中断时也不会有暂时状态
    隔离性(isolation)          # 事务间不干扰
    持久性(durability)         # 提交结果是永久的
索引存储
    B+ tree
    LSM(log-structured merge) tree
    fractal tree
OLTP和OLAP
    CAP(一致性、可用性、分区容错性)中, OLTP要求ca或cp, OLAP要求ap
    OLTP要求写优化, OLAP要求查优化
    OLTP要求优化latency, OLAP要求优化throughput
    OLTP基于row, OLAP基于column
    OLTP看中IOPS, OLAP看中data-size传输
分布式数据库
    面临问题
        ACID
        CAP
        scale out
        self-healing
        运维友好
        sql
        事务
        性能
        api用明文或二进制
        升级方案
        硬件,网络,网络模型,存储模型,语言
        分布式协议,压缩方案,ha,api,运维方案,存储计算分离,缓存方案

rds #

# relational database service
缺点
    阻抗失谐    # 和内存中的模型存在差异
安全
    sql注入   # 应该写符号编译sql
范式
    # Normal Form 用于避免冗余数据
    第一范式(1NF)
        列不可再细分列(原子性)
    第二范式(2NF)
        必须有主键,允许联合主键
        其它列依赖完整主键(不能只依赖一部分)
    第三范式(3NF)
        其它列直接依赖主键(非传递依赖,如A依赖B, B依赖主键)
实例
    postgres
    sqlserver
    mysql
    mariadb
    percona
        # mysql分支, Oracle发布的最接近官方mysql的发行版
    drizzle
        # mysql分支
    oracle
    db2
    oceandb
    h2database
        # java编写,可嵌入java使用
    tidb

sqlite #

命令
    sqlite3 数据库文件
语法
    .table              # 查看所有表
    .schema             # 查看建表语句

sql #

语法
    注释
        --      # 单行注释
        /**/    # 多行注释
    单引号
        字符串大小写敏感
    双引号
        转日期时, 双引号直接显示。to_char(sysdate,'yyyy "年" mm "月" dd "日" day')
    表别名不加as关键字, 有别名后原名无效
    oracle
        ||      # 管道符号
            select ename || '的薪水是' || sal from emp;
定义(DDL, data definition language)
    create database db1             # create or replace
        default character set utf8          # 默认编码
        collate utf8_general_ci;    # 校对规则(排序), ci(case insensitive)大小写不敏感, cs(case sensitive)大小写敏感
    create table `tb1`(           # create or replace
        `id` int unsigned unique not null auto_increment,
            # `id` int unsigned not null primary key,
        `id2` int unsigned,
        `name` varchar(20),
        `age` int unsigned,
        `birthday` date,
        primary key(`id`),          # 主键
        key idx_tb1_name (`name`),   # 索引
        foreign key(`id2`) references `tb2`(id) on delete cascade on update cascade     # 外键、级联删除、级联更新, 不要用
        )character set utf8 collate utf8_general_ci
        engine=innodb default charset=utf8;
    create table person like student;           # 复制表结构
    create table emp1 as select * from emp;     # 复制内容
    create view tb1_v (a,b) as select a, b from tb1 #  create or replace
    create synonym tb2 for tb1;     # 同义词

    drop database db1;
    drop table tb1
        purge;              # 加purge不放入回收站
    drop synonym tb1;

    truncate table tbq;


    alter database db1
        character set gbk
        collate gbk_chinese_ci;        # 更改数据库的编码
    alter table tb1
        add column sex char(1);
    alter table tb1
        add constraint pr_id primary key (id);   # 添加主键
    alter table tb1
        add constraint fk_id2 foreign key (st_id) references tb2(id);  # 添加外键
    alter table tb1
        rename to tb2;
    alter table tb1
        change sex gender char(1);      # 只能改名,但类型必须写
    alter table tb1
        modify birthday varchar(20);    # 只能改类型
    alter table tb1
        convert to character set utf8 collate utf8_general_ci;  # 转换表编码
    alter table tb1
        drop column name;
    alter table field1
        auto_increment = 5;             # 更改自增长初始值


    rename table tb1 to tb2;

    desc tb1;


    mysql
        use db1

        source a.sql            # 批执行

        show status [from schema_name];         # 服务器状态
        show databases;
        show create database db1;
        show tables;
        show create table tb1;
        show processlist                        # 查看当前连接
        show VARIABLES LIKE "general_log%"      # 查看变量 
            "version"                           # 显示版本
            "autocommit"                        # 事务开启状态 0 off 1 on, set autocommit=off 或 0
        show character set                      # 显示所有字符集



        select @@sql_mode                       # 查看变量
        select @@tx_isolation                   # 查看事务隔离级别
        select
        select VERSION()                        # 显示版本

        set sql_mode = ''                       # sql_mode定义支持的sql语法,数据校验。
        set names 'gbk';                        # 设置终端编码, 等价character_set_client=gbk 与 character_set_results=gbk
        set global general_log = 'ON'           # 设置记录所有sql

    oracle
        create table tb1 (
            sex char(1) check(sex in (0, 1))        # check约束
        show user                   # 显示用户名
        show recyclebin             # 回收站
        purge recyclebin            # 闪回文件
        oracle表创建时自动添加伪列
            rowid       # 唯一,指向当前记录
            rownum      # 唯一,字段列名, 从1开始,永远连续。
                # 支持比较符号 <, <=(可以比较=1)。取别名后可以比较 >, =


操作(DML, data manipulation language)
    # 和DQL, data query language, select、from、where
    insert into tb1
        values (3, 'a', null);
    insert into tb1
        select * from tb2;
    insert into tb1(name)
        values ('a'),('b');
    insert into tb1(a, b)
        select c, d from tb2

    update tb1
        set name='a'

    delete from tb1


    select * from outrun.employee;      # 限定数据库名
    select field1 as f1 from tb1 as t1
    select a, b into tb2 from tb1;
    select distinct (a+b) as c from tb1
        # select distinct sum(price) as s
    子查询
        # 要求数量和类型匹配
        # 不能利用索引(join可以), 不形成笛卡尔积

        where a < (select max(a) from tb2)
            # 单行符号 =、<、>
        where a in ()
            # 多行符号 in、any、all
            where a < any ()    # 小于一个就true
            where a < all ()    # 小于所有才true



    where a=1 and b=2                   # where后不能出现列的别名,可以出现表的别名
        a=1 or b=2
            # <>表示!=
            # =可设置日期
        a in (1,2)
            # a not in (1,2)
        a between 1 and 2
            # a not between 1 and 2
        a like 'a%'
            # 不能用*
            # % 匹配任意个字符
            # _ 匹配一个字符
            # \ 转义 _ 或 %
        a regexp '^.*d.*$'
            # 匹配正则
        a is null
    order by    # null看作最大值
        a asc   # 升序
        a desc  # 降序
    group by
        select a, count(b), avg(c) from tb1     # group by的select元素都是聚合函数
            where b > 0
            group by a
            having count(b) > 2                 # having使用聚合函数条件
        select a from tb1                       # 子查询
            where b in (select b from tb2 where c='c')
            group by a
            having count(distinct b) = (select count(*) from tb2 where c='c')


    select执行过程
        # 每步都产生虚拟表
        from 组装数据
            join
            on
        where 筛选
        group by 划分
        # with,  with是sql server的语法
        计算聚合函数
        having 筛选
        计算表达式
        select 字段
            distinct
        order by 排序
        top

    oracle
        insert into tb1 values(&id, '&s')                   # &是占位符,字符型数据加''
        alter table tb1 rename column field1 to field2

    常用
        分页
            select * from tb1 limit 0,1         # mysql, 从0开始,查找1条


            select * from                       # oracle
                (select rownum r, a from tb1 where rownum<=20)
            where r > 10

            select * from                       # oracle,  效率低
                (select  rownum rn, a from tb1)
            where rn between 21 and 40


            select rownum,emp.* from emp        # oracle, 效率低
                where rownum <=4
            minus
            select rownum,emp.* from emp
                where rownum <=2;

控制(DCL data control language)

    grant all privileges on db1.tb1         # 授权
        # grant insert,delete,update,select,create on db1.tb1
        to 'user1'@'host1'          # localhost本地 , %代表远程
        identified by 'pwd1'
        with grant option;          # 有授权权限
    grant select any table      # oracle
        to user1
    revoke select any table     # oracle
        from user1

    revoke privilege ON db1.tb1 from 'user1'@'host1';       # 撤销权限
    flush privileges;        # 提交授权修改, oracle不用flush直接生效


    oracle
        alter user user1 account unlock             # 解锁用户
        alter user user1 identified by user1        # 改密码
        conn / as sysdba                            # 换角色

事务
    start transaction;
    savepoint a;
    rollback to [savepoint] a;
    rollback;
    commit;

聚合函数
    avg()
    count()
    max()
    min()
    sum()


连接(join)
    内连接(inner)
        # 带条件的交叉连接
        # 只查出符合条件的记录
        select * from tb1 a         # 显示
            inner join tb2 b
            on a.c_id=b.c_id
        select * from tb1 a, tb2 b  # 隐示
            where a.c_id=b.c_id
        自连接     # 表中有层次关系。自连接无中间表, 效率快
            select a.c, b.d from course as a, course as b
                where a.c=b.d
    外连接(outer)
        # 以一表为基准,查另一表
        # 可查出不符合条件的记录(另一表无对应值,标记成null)
        左外连接
            # 以左为基准
            select * from tb1 as a
                left [outer] join tb2 as b
                on a.c_id=b.c_id

            select a.c_id       # oracle
            from tb1 a, tb2 b
            where a.c_id = b.c_id(+)
        右外连接
                right [outer] join
        全外连接
            # full [outer] join, 只oracle支持
            # 先左连接再右连接,取的是交集
            select * from a
                full join b
                on a.c_id=b.c_id
    交叉连接(cross)     # 笛卡尔积
        # 有where条件时,会先生成where查出的两个表
        select * from tb1 a
            [cross] join tb2 b
            where a.c_id = b.c_id;
    自然连接(natural)
        # 自动检查相同名称的列,类型会隐式转换,不能指定显示列(或用*)、不能用on语句
        # 每种连接名称前加natural都是自然连接
        select * from tb1 a
            natural innter join tb2 b
集合
    # 数量,类型匹配
    # 前语句别名可用,后语句别名不可用
    select a, b from tb1
        union [all] select a, b from tb2    # 并集, all 允许重复
            # intersect 交集
            # minus 差集

约束(constraint)
    not null
    unique
    primary key
        primary key unique, not null auto_increment
        primary key(col1, col2)     # 联合主键
    foreign key
        constraint fk_id2
            foreign key(id2) references tb2(id)
                # 被引用的列要建索引
                # 被引用的记录不可删除
                # 被引用的值要级联修改
            on update cascade
            on delete cascade
                # 级联约束
    检查约束    # oracle支持

存储过程 #

优势
    高效, 首次运行进行预编译
    模块化
    更快执行,大量sql时,比sql快
    减少网络流量
    安全机制
        针对过程授权
        调用时看不到语句信息和数据
        避免sql注入     # 参数视为文字
        可对过程加密
劣势
    不可移植
    需要专人维护
    逻辑变更时修改不灵活

触发器 #

用途
    表级联更改
    实现比check约束复杂的逻辑
    强制执行业务规则
    评估修改后表状态,执行操作
基础
    同一表不能建立2个相同类型触发器

视图 #

特点
    优点
        简化查询
        提供独立访问
        限制访问
    查看时,生成sql查看, 有即时性
    更新视图表级联
        不能更新的视图包含元素
            组函数
            distinct
            group by
            rownum
    grant可授权
    不能与表名重名
    mysql保存在information_schema.views中
    删除不放回收站

    CREATE [OR REPLACE] [ALGORITHM = {UNDEFINED | MERGE | TEMPTABLE}]       # TEMPTABLE是临时表,不能更新
        VIEW view_name [(column_list)]
        AS select_statement
        [WITH [CASCADED | LOCAL] CHECK OPTION]                      # 通过该视图更改的数据,可再通过该视图查看到(满足视图的限制)
    o->
    CREATE VIEW test.v AS SELECT * FROM t;
    o->
    CREATE VIEW v AS SELECT qty, price, qty*price AS value FROM t;                # 可以计算
    o->
    CREATE VIEW v AS SELECT CHARSET(CHAR(65)), COLLATION(CHAR(65));                # 可以联合
    o->
    CREATE ALGORITHM = MERGE VIEW v_merge (vc1, vc2)
        AS SELECT c1, c2 FROM t1 WHERE c3 > 100

        查询解释
            SELECT * FROM v_merge WHERE vc1 < 100; 会执行
            SELECT c1, c2 FROM t WHERE (c3 > 100) AND (c1 < 100);


    ALTER [ALGORITHM = {UNDEFINED | MERGE | TEMPTABLE}]
        VIEW view_name [(column_list)]
        AS select_statement
        [WITH [CASCADED | LOCAL] CHECK OPTION]              # CASCADED 忽略主外键关系

    DROP VIEW [IF EXISTS]
        view_name [, view_name] ...
        [RESTRICT | CASCADE]

    SHOW CREATE VIEW view_name

索引 #

特点
    第一次查询时创建
    加快查询的速度,表删除时索引自动删除
    primary key 与 unique 自动建立
命中
    where 中添加对应索引的条件, 只能从前向后命中
是否使用
    使用
        分布广
        经常在where中出现
        表经常访问
    不使用
        表小
        不经常出现的列
        经常更新的字段
类型
    index
    unique
    primary key

CREATE INDEX index_name ON table_name (column_list)         # 创建索引,primary key已有索引
CREATE UNIQUE INDEX index_name ON table_name (column_list)

ALTER TABLE table_name ADD INDEX index_name (column_list) # 创建索引,列名逗号分隔。index_name缺省时,根据第一个索引列取名
ALTER TABLE table_name ADD UNIQUE (column_list)
ALTER TABLE table_name ADD PRIMARY KEY (column_list)

DROP INDEX index_name ON talbe_name
ALTER TABLE table_name DROP INDEX index_name        # 等价于前一个
ALTER TABLE table_name DROP PRIMARY KEY

show index from tb1;
show keys from tb1;
    Table         # 表的名称。
    Non_unique    # 如果索引不能包括重复词,则为0。如果可以,则为1。
    Key_name      # 索引的名称。
    Seq_in_index  # 索引中的列序列号,从1开始。
    Column_name   # 列名称。
    Collation     # 列以什么方式存储在索引中。在MySQL中,有值‘A’(升序)或NULL(无分类)。
    Cardinality   # 索引中唯一值的数目的估计值。通过运行ANALYZE TABLE或myisamchk -a可以更新。基数根据被存储为整数的统计数据来计数,所以即使对于小型表,该值也没有必要是精确的。基数越大,当进行联合时,MySQL使用该索引的机会就越大。
    Sub_part      # 如果列只是被部分地编入索引,则为被编入索引的字符的数目。如果整列被编入索引,则为NULL。
    Packed        # 指示关键字如何被压缩。如果没有被压缩,则为NULL。
    Null          # 如果列含有NULL,则含有YES。如果没有,则该列含有NO。
    Index_type    # 用过的索引方法(BTREE, FULLTEXT, HASH, RTREE)。
    Comment       # 更多评注。

序列 #

# 共享对象唯一的数值,不一定连续
create sequence tb1_seq
    INCREMENT BY 10              # 步长是10
    START WITH 120               # 从120开始
    MAXVALUE 9999                # 最大到9999
    NOCACHE                      # 不缓存序列的值(缓存是先创建很多再取出,不缓存则是什么时候取,什么时候创建)
    NOCYCLE;                     # 到最大值的时候是否循环

select seq.nextval from dual                # nextval下一个序列 currval当前序列  第一次使用必须是nextval
insert into emp(id) vallues(seq.nextval);   # 使用
alter sequence tb1_seq increment by 10;
    start with 100;                         # 错误 ,不能变更启动序列,只能在创建序列时指定
drop sequence seq

性能优化 #

设计
    库
        分库
            拆微服务
            主从      # master不拆,slave树形
            索引与数据分库
    表
        不要代价高的关系(外键、级联)
        字段可冗余,为了提高性能,但要考虑同步。不能是频繁修改的字段,不是varchar和text
        单表行数超过500万或意表容量超过2GB,才分库分表
        分表  # 垂直分字段,水平分记录
            表名加hash到多表
            partitioning key字段分表    # proxy网关分流
                时间
                地点
            建lookup table查找对应表
            冷热分离
        用表变量代替临时表
        表变量数据大时,只有主键索引
        大量重复引用大型表或常用表数据时,可创建临时表。一次性事件,最好导出表
        临时表时数据大时, 用select into代替create table, 避免log过多
        临时表最后要先truncate, 再drop, 避免表较长时间锁定
    类型
        尽量not null
        数字类型尽量用
        char存几乎定长字符串类型
        varchar变长字符串,不预先分配空间,长度不要超过5000
        text存大于5000,独立出表用主键对应,避免影响其它字段索引效率
        bool用unsigned tinyint
        小数类型用decimal,不用float double
            # float和double存储的时候,存在精度损失的问题
            # 长度超过decimal范围,拆成整数和小数分开存
        合适的字符长度,不但节约表空间,节约索引存储,更提升检索速度
            unsigned tinyint    0到255
            unsigned smallint    0到65535
            unsigned int    0到42.9亿
            unsigned bigint    0到10的19次方
    索引
        有唯一特性,都建唯一索引
            # insert速度损耗可以忽略,但明显提高查找速度
            # 不建唯一索引,总会有脏数据产生
        where与order by涉及的列建索引
        建组合索引时,区分度最高的在左边
            where a=? and b=? ,a列几乎接近唯一值,只需要建idx_a索引
            非等号和等号混合时,等号是最左边,如where a>? and b=?, 那么b在索引最前列
        字段值大量重复时,索引作用不大
        索引降低insert与update效率
        索引数据列少更新           # 数据列为表存储方式,更新会调整整表存储
        varchar建索引,要指定索引长度
            一般字符串数据,长度为20的索引,区分度高达90%以上
            count(distinct left(列名,索引长度)) / count(*)来计算
语句
    where放弃索引,全盘扫描
        比较符
            in      # in元素尽量控制在1000内
            not in
            # exists代替in
                select num from a where num in(selct num from b)    改为
                select num from a where exists(select 1 from b where num=a.num)
            is null
            is not null
            <>
            or
            like '%a'模糊开头

        where对字段用表达式或运行函数
            where num/2=100 改为
            where num = 100*2

            where year(admin_time)>2014 改为
            where admin_time>'2014-01-01'
        where使用参数       # 因为运行时解析局部变量,访问计划在编译时进行
            select id from t where num=@num 改为
            select id from t with(index(索引名)) where num=@num    # 强制使用索引
    select
        不要写无意义查询
            select a into #t from t where 1=1 改为
            create table #t
        不要select *             # 增加查询分析器解析成本,增减字段容易与resultMap不一致
        不select for update      # 长期锁定行(游标默认都用)
            不要用游标
    函数
        使用count(*)统计行数
            用count(distinct col1, col2)来计算不重复
        sum(col)会返回null,如下解决
            SELECT IF(ISNULL(SUM(g)), 0, SUM(g)) FROM table1
        使用ISNULL()来判断NULL
            # NULL与任何值比较都为NULL
业务
    sql优化至少到range级别
        # explain结果type=
        # all 全表扫描
        # index 扫描整个索引表,几乎相当于全表扫描
        # range 用索引选择范围
        # ref 非唯一索引扫描
        # eq_ref 唯一索引扫描
        # consts 索引一下就找到,单表中最多有一个匹配行(主键或唯一索引), 在优化阶段即可读取到数据
        # system 表只有一行
    库
        不在数据库写逻辑           # 不使用存储过程, 难调试和扩展,没有移植性
        正确锁类型                # 隐式锁、显式锁、行锁、页锁、范围锁、表锁、数据库锁
        全球化用utf-8,要使用表情,用utfmb4
            SELECT LENGTH("轻松工作") 返回 12
            SELECT CHARACTER_LENGTH("轻松工作") 返回4
    事务
        不要多阶段提交             # 更好的拆分表,而不多阶段提交延长单一数据库生命
        避免大事务
        连接释放
    crud
        TRUNCATE快,但无事务不触发trigger, 不要在开发代码中使用
        修改数据时,先select,避免误删除和修改
        分页时count为0直接返回
        用覆盖索引来变相加快查询,如explain的结果,命中时出现using index
        避免返回大量数据
        order by注意利用索引的有序性,order by最后的字段是组合索引的最后,避免file_sort
            如 where a=? and b=? order by c; 索引 a_b_c
            有范围查找时,有序性无法利用,如 where a>10 order by b
    联合
        多表联合查询拆分多个query     # 容易锁表和阻塞
        禁止三表join
            join的字段类型要一致
            被关联的字段需要有索引
            注意sql性能
        join时,小结果驱动大结果      # left join小表在左
            优化前
                select * from admin
                left join log on admin.admin_id = log.admin_id
                where log.admin_id>10
            优化后
                select * from
                    (select * from admin where admin_id>10) T1
                left join log on T1.admin_id = log.admin_id
mysql
    引擎选择
    limit 1
        只查一条时,加limit 1, 引擎会找到一条马上返回
    limit基数大用between, 分页时要找到id, 避免offset之前全查的问题
        优化前
            select * from admin order by id limit 10000,10
        优化后
            select * from admin where id between 10000 and 10010 order by id
        子查询id
            select a.* from 表1 a, (select id from 表1 where 条件 limit 100000,20) b where a.id=b.id

nosql #

介绍
    aggregate-oriented (面向聚合)
        键值
        文档
        列族
    relationship-oriented (面向关系)
        图
特点
    少约束(schemaless)
    应用程序数据库(作为微服务的数据库来解耦)
    聚合(aggregate)
        # 领域驱动设计中提出
        # 图除外
    图支持事务
    牺牲一部分一致性和持久性
问题
    存在不一致窗口
    会话一致性问题
兼容
    物化视图来处理更新
    实时BI, 来更新中间关系聚合
    一致性
        锁
        条件更新(更新前检查)
            版本戳
                # http 中的etag
        写入仲裁与读取仲裁
            复制因子大于某值时认为写入完成
            读取多于某值个节点数据并相同时,认为读到最新数据
        用zookeeper等外部“事务”程序库同步读写操作

#

介绍
    领域
    关系是一等公民
    大部分不支持分布式
    Gremlin,Cypher 查询语言
适用
    互联数据
    运输等基于位置的服务
    推荐引擎
不适用
    经常更新
工具
    flockDB
            # 仅支持单深度关系及邻接表
    hyperGraphDB
    infiniteGraph
    allegroGraph
    orientdb
    pregel
        # google图数据库

neo4j #

介绍
    使用zookeeper
特点
    完全兼容ACID
    主从复制
    副本从节点
        从节点写数据,先同步到主节点, 再由主节点分发

配置 dbms.connector.bolt.enabled=true dbms.connector.bolt.listen_address=0.0.0.0:7687 dbms.connector.http.enabled=true dbms.connector.http.listen_address=0.0.0.0:7474 # 远程访问 cql 数据类型 boolean byte # 8位整数 short # 16位整数 int # 32位整数 long # 64位整数 float # 32位浮点数 double # 64位浮点数 char # 16位字符 string 命令 create # 创建, 自动生成属性, 最大约为35亿 CREATE (dept:Dept:Dept2 { deptno:1,name:“a”}) # 节点名:多标签 {属性} CREATE (p1:Profile1)-[r1:LIKES]->(p2:Profile2) # 2节点,1关系

            MATCH (cust:Customer),(dept:Dept)
            WHERE cust.id = 1 AND dept.deptno= 1 
            CREATE (cust)-[r:Do{a:1}]->(dept)  
            RETURN cust,dept,r
                # match并创建关系
        merge                   # 不存在时才创建
            MERGE (gp2:GoogleProfile2{ Id: 201402,Name:"Nokia"})
        set                     # 更新
            MATCH (dc:DebitCard)
            SET dc.atm_pin = 3456
            RETURN dc
        delete                  # 删除节点,关系
            MATCH (cc: CreditCard)-[rel]-(c:Customer)
            DELETE cc,c,rel
        remove                  # 删除属性
            MATCH (dept:Dept)
            REMOVE dept.dname
            RETURN dept
        match                   # 查询
            MATCH (dept: Dept)
            RETURN dept
                # 节点名:标签名, return 节点名.属性名
            MATCH (dept: Dept)
            RETURN dept.deptno,dept.dname
                # 只查属性,不形成图
            MATCH ( cc: CreditCard)-[r]-()
            RETURN r
                # 全集
        return
            RETURN dept
                # 节点名
            RETURN dept.deptno,dept.dname as dname
        where
            WHERE emp.name = 'Abc' OR emp.name = 'Xyz'
            WHERE cust.id = "1001" AND cc.id= "5001" 
            WHERE e.id is not null
            WHERE e.id in [1,2]

            MATCH (emp:Employee) 
            WHERE emp.name = 'Abc' OR emp.name = 'Xyz'
            RETURN emp
                # 加where
        order by
            MATCH (emp:Employee)
            RETURN emp.empid,emp.name,emp.salary,emp.deptno
            ORDER BY emp.name DESC
        union
            MATCH (cc:CreditCard) RETURN cc.id,cc.number
            UNION
            MATCH (dc:DebitCard) RETURN dc.id,dc.number
        union all
        limit和skip
            MATCH (emp:Employee) 
            RETURN emp
            LIMIT 2
            SKIP 2
        create index
            CREATE INDEX ON :Customer (name)
                # 建索引, 标签(属性)
        drop index
            DROP INDEX ON :Customer (name)
                # 删除索引
        create constraint
            CREATE CONSTRAINT ON (cc:CreditCard)
            ASSERT cc.number IS UNIQUE
                # 约束
        drop constraint
            DROP CONSTRAINT ON (cc:CreditCard)
            ASSERT cc.number IS UNIQUE
    函数
        信息
            RETURN ID(movie),TYPE(movie)
                # 显示id, 标签
        字符串
            RETURN LOWER(e.name)
            RETURN SUBSTRING(e.name,0,2)
        聚合
            RETURN COUNT(*)
            RETURN MAX(e.sal),MIN(e.sal)
            RETURN SUM(e.sal),AVG(e.sal)
        关系
            RETURN STARTNODE(r) # 返回开始节点
            RETURN ENDNODE(r)

HugeGraph #

百度开源

NebulaGraph #

分布式图数据库

TigerGraph #

列族 #

特点
    键空间
适用
    事件记录
        # 事件id为行
    内容管理
    计数器
    带过期的列
不适用
    ACID事务
    多行数据聚合
工具
    cassandra
    hbase
    amazon simpleDB
    hypertable
    bigtable
    clickhouse
        # 用于OLAP, 实时分析

cassandra #

特点
    适用大规模数据
    良好的分布式扩展性
    功能比key-value丰富,不如mongo
    写快于读
    不稳定
    没有主节点,所有节点平等
    查询语言CQL
    列TTL(秒)
命令
    cqlsh localhost 9042
数据库命令
    use aaa
        # 用aaa键空间

hbase #

特点
    hdfs存储,分布式,面向列
    可利用map reduce
特点
    多版本
    列权限控制
    多个列划分为列族,可设置保留多少版本
    多行划分为region
    空列不占空间,可稀疏存储
    无类型,所有类型都是字符串
    行一致性,一行数据在一个server
    查询方式有限:rowkey, rowkey的range, 全表扫描
    协处理器coprocessors
        观察者observer(监听器)
        终端endpoint(rpc调用代码)

文档 #

适用
    事件记录
    内容管理
    网站分析与实时分析数据
    电子商务中产品或订单
不适用
    事务
    持续变化的数据
工具
    couchDB
    orientDB
    ravenDB
    terrastore
    xml数据库
    mongoDB
    memDB
        # 带事务的mongo
    tokumx

couchDB #

特点
    apache托管,  alang语言开发的,面向文档的分布式数据库
    json结构,易于存储cms, 电话本,地址本等半结构化数据。存储类似于lucene的index
    易添加,不易修改
    主主双向复制

键值 #

适用
    session
    用户配置信息
    购物车
不适用
    数据间关系
    多项操作的事务
    模糊键查询
    对集合关键字操作
工具
    redis
    riak
        # 类cassandra
    berkeleyDB
    levelDB
        # google
    memcached
    project voldemort
    tokyo cabinet
    rocksDB
    groupCache  # go编写

时序 #

influxDB    # go编写

newsql #

工具
    分布式
        google spanner
        voltdb
        clustrix
        nuodb
        tidb    # go编写
    h-store
    foundationDB
    scalebase
    dbshards
    scalearc
    tokudb
    memsql

tidb #

流式数据库 #

piplelineDB
    # 依赖zeromq, 记录时间段内的事件

全文索引 #

Lucene
ElasticSearch
Solr
Sphinx

proxy #

mycat #

# 目录结构
        bin
                mycat                        # 服务器启动等
        conf
                wrapper.conf                # jvm配置参数(如分配系统资源)
                server.xml                # 服务器参数,用户授权
                schema.xml                # 逻辑库,表,分片的定义.修改后要重启
                log4j.xml                # 配置输出到logs/mycat.log的日志
        logs
                mycat.log                # 日志(每天一个日志文件), 可调整输出级别

# 默认值
        默认数据端口: 8066
        默认管理端口: 9066

# 配置
    wrapper.conf                # jvm配置参数(如分配系统资源)
    server.xml                # 服务器参数,用户授权
    schema.xml                # 逻辑库,表,分片的定义.修改后要重启
    log4j.xml                        # 配置输出到logs/mycat.log的日志

    mysql
        linux版数据库设置大小写不敏感,否则会发生表找不到的问题
                my.cnf
                        [mysqld]
                        lower_case_table_names = 1

# 例子
    server.xml
            <mycat>
            <user name="test">
                    <property name="password">test</property>
                    <property name="schemas">TESTDB</property>
            </user>
            </mycat>

    schema.xml
            <mycat>
            <schema name="TESTDB" checkSQLschema="false" sqlMaxLimit="100">
                    <table name="travelrecord" dataNode="dn1,dn2,dn3" rule="auto-sharding-long" />
                    <table name="employee" primaryKey="ID" dataNode="dn1,dn2" rule="sharding-by-intfile" />
                    <table name="company" primaryKey="ID" type="global" dataNode="dn1,dn2,dn3" />
                    <table name="goods" primaryKey="ID" type="global" dataNode="dn1,dn2" />
                        <table name="hotnews" primaryKey="ID" dataNode="dn1,dn2,dn3" rule="mod-long" />
                            <table name="customer" primaryKey="ID" dataNode="dn1,dn2" rule="sharding-by-intfile">
                                            <childTable name="orders" primaryKey="ID" joinKey="customer_id" parentKey="id">
                                                    <childTable name="order_items" joinKey="order_id" parentKey="id" />
                                            </childTable>
                                            <childTable name="customer_addr" primaryKey="ID" joinKey="customer_id" parentKey="id" />
                            </table>
            </schema>
            <dataNode name="dn1" dataHost="localhost1" database="db1" />
            <dataNode name="dn2" dataHost="localhost1" database="db2" />
            <dataNode name="dn3" dataHost="localhost1" database="db3" />
            <dataHost name="localhost1" maxCon="1000" minCon="10" balance="0"
                    writeType="0" dbType="mysql" dbDriver="native">
                    <heartbeat>select user()</heartbeat>
                    <writeHost host="hostM1" url="centos6.5_1:3306" user="root" password="asdf">
                    </writeHost>
            </dataHost>
            </mycat>

    rules.xml
            <mycat>
                    <tableRule name="sharding-by-intfile">
                    <rule>
                            <columns>sharding_id</columns>
                            <algorithm>hash-int</algorithm>
                    </rule>
                    </tableRule>
                    <tableRule name="mod-long">
                    <rule>
                            <columns>id</columns>
                            <algorithm>mod-long</algorithm>
                    </rule>
                    </tableRule>
                    <function name="hash-int" class="org.opencloudb.route.function.PartitionByFileMap">
                            <property name="mapFile">partition-hash-int.txt</property>
                    </function>
                    <function name="mod-long" class="org.opencloudb.route.function.PartionByMod">
                            <property name="count">3</property>
                    </function>
            </mycat>

    partition-hash-int.txt
            10000=0
            10010=1

    sql
            create table employee (id int not null primary key,name varchar(100),sharding_id int not null);
            insert into employee(id,name,sharding_id) values(1,'leader us',10000);
            insert into employee(id,name,sharding_id) values(2,’me’,10010);
            insert into employee(id,name,sharding_id) values(3,’mycat’,10000);
            insert into employee(id,name,sharding_id) values(4,’mydog’,10010);

            create table company(id int not null primary key, name varchar(100));
            insert into company(id,name) values(1,'hp');
            insert into company(id,name) values(2,'ibm');
            insert into company(id,name) values(3,'oracle');

            create table customer(id int not null primary key, name varchar(100), company_id int not null, sharding_id int not null);
            insert into customer (id,name,company_id,sharding_id )values(1,'wang',1,10000);
                    insert into customer (id,name,company_id,sharding_id )values(2,'xue',2,10010);
                    insert into customer (id,name,company_id,sharding_id )values(3,'feng',3,10000);

            create table orders (id int not null primary key ,customer_id int not null,sataus int ,note varchar(100));
            insert into orders(id,customer_id)values(1,1);
            insert into orders(id,customer_id)values(2,2);

            create table travelrecord( id bigint not null primary key,username varchar(100), traveldate DATE, fee decimal, days int);
            insert into travelrecord(id,username,traveldate,fee,days)values(1,'wang','2014-01-05',510.5,3);
            insert into travelrecord(id,username,traveldate,fee,days)values(5000001,'wang','2014-01-05',510.5,3);

            create table hotnews(id int not null primary key, title varchar(400), created_time datetime);
            insert into hotnews(id,title,created_time)values(1,'first',now());
            insert into hotnews(id,title,created_time)values(5,'first',now());

            create table goods(id int not null primary key,name varchar(200),good_type tinyint,good_img_url varchar(200), good_created date, good_desc varchar(500), price double);

            create table order_items(id int not null primary key, order_id int not null);
            insert into order_items(id, order_id) values(1,1);
# 经验
    o-> 数据库上的数据修改(权限修改)立即生效
    o-> 支持跨库事务,且等待主从复制完成后完成事务(如全局表的复制)
    o-> virtualbox4.3下配置的mycat节点不能子表插入
    o-> 可以配置jdbc数据库进行远程数据调用
    o-> childTable中的joinKey与parentKey是必须字段, childTable不能配置dataNode
    o-> 同一个childTable出现在多个主表时(相当于mysql的多个外键),会出错,提示该childTable重复创建
    o-> childTable不能配置dataNode, 默认和主表存的dataNode相同
    o-> 虽然childTable只能配一个,但mysql里可以配置多个外键,但要求外键关联的表配置>在相同的dataNode上
    o->  配置在两个dataHost中的表, show tables 时表名会显示两遍
    o-> table不配置rule默认数据每个dataNode存一份,但是mycat查询时显示同id的两份数据,此方法不可用
    o-> table不配置,不可以创建
    o-> 全局序列号名称必需大写
    o-> 不同dataNode中的普通表不可以关联查询
    o-> 同样配置dn1, dn2 的两个普通外键关系表之间数据插入可能会出错(如: 表2数据在dn1中, 其外键关联表2在dn2中的数据时)