从“数据孤岛”到“星辰大海”的理论基础课
为什么我们需要一种“新”的数据库?
图数据库到底解决什么痛点?
大家大一学过 MySQL,数据存在“表”里(行和列)。
在关系型数据库中,表与表之间的关系是隐式的(通过外键)。
每次查询“关系”,数据库都需要重新计算一次映射,就像每次找人都要翻一遍全国户口本,非常耗时。
图数据库不使用死板的表格,而是像画思维导图一样,直接把事物和它们之间的关联“画”出来并存储。
在这里,关系和数据本身一样重要!
Neo4j 是目前全球最流行、最强大的图数据库管理系统之一。
相比传统数据库,它在处理以下场景时性能提升上千倍:
要学好图数据库,必须死死记住这四个基本零件(就像乐高积木一样):
(Node)
(Relationship)
(Property)
(Label)
节点就相当于传统数据库表中的“一行数据”。
没有关系的图只是一堆散落的沙子。关系让数据产生了联系。
无论是“节点”还是“关系”,都可以拥有自己的属性。
标签是用来对节点进行分组和归类的。
Person(人),同时也可以是 Student(学生)。
和 Neo4j 沟通的官方语言。
一门“画画”一般的编程语言!
就像关系型数据库听得懂 SQL 语句(SELECT, INSERT)一样,Neo4j 听得懂的话就叫 Cypher。
Cypher 是一种声明式图数据库查询语言。它的设计初衷就是为了让人类和电脑都能直观地理解图数据。
Cypher(赛弗)的名字来源于电影《黑客帝国》中的角色。
特点:
Cypher 最独特的地方在于,它的代码长得像颜文字(ASCII 艺术)。它用键盘上的符号直接“画”出图形!
如果要表示:“一个叫张三的人,认识一个叫李四的人”。
Cypher 代码长这样:
(张三)
圆括号代表节点
-[认识]->
箭头和方括号代表带方向的关系
(李四)
圆括号代表目标节点
磨刀不误砍柴工。
在写代码前,先了解它的基本规则。
Cypher 中的数据类型可以分为三大类,就像我们生活中的不同物资:
最基础的值,可以存入节点和关系的属性中。
代表图结构本身的类型(节点、关系等)。
用来把多个数据打包在一起的类型。
' ' 或双引号 " " 包裹。比如 "张三"。true(真)或 false(假)。请注意!字符串必须加引号!
如果你写 name: 张三,程序会报错。必须写成 name: "张三" 或者 name: '张三'。
而数字和布尔值千万不能加引号,加了就变成文字了!
注意:结构类型不能作为属性保存!你不能把一个“节点”存进另一个“节点”的属性里。
把一组有顺序的数据打包在一起。
[1, 2, 3]["苹果", "香蕉", "橘子"]hobby: ["唱歌", "跳舞"]。由一组键值对(Key-Value)组成的集合。
{name: "李四", age: 22}在 Cypher 中,null 表示缺失的或者未知的值。
age 属性,你强行查询它的 age,不会报错,只会返回 null。我们在给变量、标签、关系类型起名字时,必须遵守规则:
Person 和 person 是两码事)_ 以外)。万一非要用包含空格或者中文字符做名字怎么办?
可以使用反引号 ( ` ) 将名字包裹起来(键盘左上角 Esc 下面的键)。
例如:
虽然规则允许你随便起名字,但在企业开发中,我们有不成文的约定,显得代码更专业:
使用首字母大写的驼峰命名法 (CamelCase)。
✅ Person, Vehicle, Company使用全大写+下划线 (UPPER_SNAKE_CASE)。
✅ KNOWS, ACTED_IN, IS_FRIEND_WITH使用首字母小写的驼峰命名法 (camelCase)。
✅ firstName, age, publishDate关键字就是 Cypher 系统内部征用的词汇,咱们自己起名字时要避开它们。
常见的操作关键字包括(也是我们稍后要重点学习的):
(注:Cypher 关键字本身不区分大小写,但规范上我们习惯全部大写,以区分于数据。)
理论结合实际!
增、查、改、删,一段段代码拆解给你看。
CREATE 关键字用于向图数据库中插入新的节点、关系或路径。
就像女娲捏泥人一样,从无到有创造实体。
解析:
圆括号 () 代表这是一个节点。n 是一个临时起的变量名(代号),为了方便后续引用它。这个节点没有任何标签和属性,非常孤独。
刚才的空白节点没有任何分类,现在我们给它贴个标签(比如:人)。
语法拆解:
冒号 : 后面的 Person 就是标签(Label)。
这句代码的意思是:创建一个节点,属于 Person 类,并暂时代称为 n。
这是平时最常用的写法,直接把数据的详细内容塞进去(使用大括号 {} 写 Map)。
语法拆解:
节点代号:n
分类标签:Person
拥有两个属性:name 是字符串张三,age 是数字20。
用箭头 -[]-> 连接两个节点!
KNOWS(认识)。since: 2020(从2020年开始认识)。MATCH 类似于 SQL 中的 SELECT。
它是图数据库中最重要的命令!
作用:在整个庞大的图谱中,“匹配”出符合你画出形状的模式(Pattern)。
注意:MATCH 通常不能单独使用,必须搭配 RETURN 把结果返回出来。
⚠️ 警告:这相当于 SELECT * FROM 所有表。如果公司数据库有上亿个节点,这条命令会让服务器卡死。平时练习时可以用。
Person 标签的数据。name 等于 '张三' 的数据。n 中,并通过 RETURN 交给用户。需求:找到“张三”认识的所有的“朋友”。
这才是 Neo4j 真正强大的地方!无需连表(JOIN),直接像顺藤摸瓜一样:找到张三,顺着向外的 KNOWS 箭头,找到另一端的节点,并把那个节点命名为 friend 返回出来!
不仅仅可以返回整个节点,还可以返回指定的属性。
通过小数点 . 就能提取具体的属性值,像表格一样返回。
为了让返回的表头更好看,可以用 AS 进行重命名。
输出结果的列名就会变成中文的“姓名”和“年龄”。
当你搜索出1万条数据,但网页一页只能显示10条时,就需要分页。
即使系统里有100个Person,也只输出前3个。
跳过前10条,取接下来的10条(即第11-20条记录)。
要删除数据,必须先 MATCH 找到它,然后再 DELETE 它。
坑点警告!
如果“张三”身上还连着和其他人的“关系线”,上面这行代码会直接报错失败!
Neo4j 决不允许出现一端悬空的孤立关系!
为了解决节点连着关系无法删除的问题,Cypher 提供了一个组合拳:DETACH DELETE(分离并删除)。
执行逻辑:系统会像剪刀一样,先咔嚓剪断“张三”身上的所有关系线,然后再把“张三”这个节点销毁,干脆利落。
同学们经常搞混这两个词:
这行代码执行后,张三这个节点还在,他的名字也还在,只是“age(年龄)”这个属性被永远删除了。
我们在 MATCH 时可以用 {age: 20} 来找20岁的人。但如果我要找“大于20岁”的人呢?大括号就做不到了。
这时候就要请出 WHERE 从句:
=, <>, <, >, <=, >=
例:WHERE n.age >= 18
(注:不等于用 <>)
AND, OR, XOR, NOT
例:WHERE n.age>18 AND n.gender='男'
STARTS WITH
ENDS WITH
CONTAINS
例:WHERE n.name STARTS WITH '张'
(查找所有姓张的人)
SET 关键字用来更新现有的节点或关系。
通过 SET,我们可以动态地给已经存在的节点贴上新的标签(使用冒号 :)。
执行后:张三不仅拥有原本的 Person 标签,又多出了 Student(学生)和 Monitor(班长)两个新标签!这就是无模式数据库的灵活性。
() 表示-[]-> 表示{} 表示: 表示下节课我们将进行上机实操,请大家做好准备!
有什么疑问随时提问,谢谢大家!