介绍

Neo4j是一个高性能的、基于Java的NoSQL图形数据库,它将结构化数据存储在网络(从数学角度称为图)上而不是传统的表中。Neo4j因其嵌入式、高性能、轻量级等优势,在数据存储、检索、分析和挖掘等方面有着广泛的应用。以下是对Neo4j的详细介绍

一、Neo4j的基本特性

  1. 高性能的图引擎:Neo4j可以被看作是一个高性能的图引擎,具有成熟和健壮的数据库的所有特性。它支持大规模可扩展性,可以处理数十亿节点/关系/属性的图,并且可以扩展到多台机器并行运行。
  2. 面向对象的网络结构:程序员在Neo4j中工作在一个面向对象的、灵活的网络结构下,而不是严格、静态的表中。这种结构使得Neo4j非常适合表示复杂、互连接、低结构化的数据。
  3. 完全的事务特性:Neo4j是一个嵌入式的、基于磁盘的、具备完全的事务特性的Java持久化引擎。它支持完整的ACID(原子性、一致性、隔离性和持久性)规则,确保数据的一致性和完整性。
  4. CQL查询语言:Neo4j使用CQL(Cypher Query Language)作为查询语言,这是一种声明性模式匹配语言,其语法简单且人性化、可读性强。CQL遵循SQL语法,使得熟悉SQL的程序员可以快速上手。

二、Neo4j的优势

  1. 性能优势:Neo4j对长程关系的查询速度快,能够迅速遍历节点与边,其遍历速度与构成图的数据量没有直接关系。此外,Neo4j还提供了非常快的图算法、推荐系统和OLAP风格的分析。
  2. 数据表示优势:Neo4j很容易表示连接的数据和半结构化数据。检索、遍历和导航更多的连接数据是非常容易和快速的。它不需要复杂的连接来检索连接的/相关的数据,因为它可以很容易地检索相邻节点或关系细节。
  3. 灵活性和可扩展性:Neo4j的图形数据模型非常灵活,可以轻松地适应不断变化的业务需求。同时,Neo4j支持大规模可扩展性,可以处理大规模的数据集。

三、Neo4j的应用场景

  1. 社交媒体:Neo4j可以用于存储和检索社交媒体中的用户关系、帖子、评论等数据,支持复杂的社交网络分析。
  2. 推荐系统:Neo4j可以根据用户的行为和偏好构建推荐系统,通过图分析发现用户之间的潜在联系和兴趣点。
  3. 身份和访问管理:使用图形数据库进行身份和访问管理时,可以快速有效地跟踪用户、资产、关系和授权。
  4. 金融风控:Neo4j可以用于金融领域的风控分析,通过图分析发现潜在的欺诈行为和洗钱网络。
  5. 其他领域:Neo4j还可以应用于知识图谱、物流网络、生物信息学等多个领域。

结构

节点(Nodes)

  • 定义:节点是图的基本单位,用于表达各种实体,如人、部门、物品等。每个节点都有唯一的ID,用于在图中唯一标识该节点。
  • 功能:节点用于存储和表示现实世界中的实体或对象,以及这些实体或对象的属性。
  • 示例:在社交网络中,节点可以代表用户;在推荐系统中,节点可以代表商品或用户。

关系(Relationships)

  • 定义:关系是图形数据库中连接节点的边,用于表示节点之间的连接、关联或依赖关系。关系可以具有方向性,即从一个节点指向另一个节点。
  • 功能:关系用于描述节点之间的相互作用或联系,是图数据库的核心组成部分。通过关系,可以轻松地遍历和查询图中的节点。
  • 属性:关系也可以包含属性,这些属性用于存储关于关系本身的信息,如关系的类型、权重、时间戳等。
  • 示例:在社交网络中,关系可以表示用户之间的好友关系、关注关系等;在推荐系统中,关系可以表示用户与商品之间的购买关系、浏览关系等。

属性(Properties)

  • 定义:属性是用于描述图节点和关系的键值对。属性以键值对的形式存在,其中键是一个字符串,值可以是任何Neo4j支持的数据类型。
  • 功能:属性用于存储节点或关系的详细信息,如节点的名称、年龄、性别等,或关系的类型、权重等。这些属性使得节点和关系更加丰富和具体。
  • 示例:在社交网络中,用户节点的属性可以包括用户名、年龄、性别等;在推荐系统中,商品节点的属性可以包括商品名称、价格、描述等。

标签(Labels)

  • 定义:标签是Neo4j中的一种元数据,用于对节点进行分类和组织。每个节点可以有一个或多个标签,这些标签用于标识节点的类型或属性。
  • 功能:通过为节点添加标签,可以更好地组织和管理数据,提高查询性能。标签可以用作索引,加快查询速度。同时,标签也使得数据模型更加灵活和可扩展。
  • 示例:在社交网络中,用户节点可以被打上“用户”或“VIP用户”等标签;在推荐系统中,商品节点可以被打上“电子产品”、“服装”等标签。

综上所述,节点、关系、属性和标签共同构成了Neo4j图形数据库的基本数据模型。通过这些元素,Neo4j能够高效地存储、检索和分析复杂的数据关系网络。

Cypher语句

Cypher是neo4j的查询语言,类似于关系型数据库中的SQL,一些关键词来源于SQL,比如:CREATE,WHERE,RETURN等,对关键词的大小写不敏感

匹配语句

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
Match (n) return n
//查询所有的数据
MATCH (n:Person) RETURN n
//该语句返回所有带有person标签的节点
MATCH (n:Person {name: 'Alice'}) RETURN n
//返回所有具有Person标签且name属性为'Alice'的节点。
MATCH (a:Person)-[:FRIEND]->(b:Person) RETURN a, b
//返回所有具有FRIEND关系且两端都是Person节点的关系对。
MATCH (n:OLT {name: "北京市转运中心"}) -- (m) RETURN n,m
//查询所有与“北京市转运中心”有关系的节点
MATCH (n:OLT {name:"北京市转运中心"}) --> (m:OLT) RETURN n,m
//查询所有"北京市转运中心"关联的一级转运中心


//分页查询网点,按照bid正序排序,每页查询2条数据,第一页
MATCH (n:AGENCY)
RETURN n ORDER BY n.bid ASC SKIP 0 LIMIT 2

//第二页
MATCH (n:AGENCY)
RETURN n ORDER BY n.bid ASC SKIP 2 LIMIT 2

创建语句

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
CREATE (n {name: $value}) RETURN n   //创建节点,该节点具备name属性,n为该节点的变量,创建完成后返回该节点
CREATE (n:$Tag {name: $value}) //创建节点,指定标签
CREATE (n)-[r:KNOWS]->(m) //创建n指向m的关系,并且指定关系类型为:KNOWS

//示例
CREATE (n {name:'迪士尼营业部'})
CREATE (n:AGENCY {name:'航头营业部'})

//创建浦东新区转运中心、上海转运中心节点,并且创建关系为:IN_LINE,创建完成后返回节点和关系
//TLT -> Two Level Transport(二级转运中心)
//OLT -> One Level Transport(一级转运中心)
CREATE (n:TLT {name:'浦东新区转运中心'}) -[r:IN_LINE]-> (m:OLT {name:'上海转运中心'}) RETURN n,r,m

//关系也是可以反向,并且可以为关系中指定属性
CREATE (n:TLT {name:'浦东新区转运中心'}) <-[r:OUT_LINE]- (m:OLT {name:'上海转运中心'}) RETURN n,r,m

合并语句

合并语句是创建语句和匹配语句的结合体,先尝试找到给定模式匹配的节点和关系,如果不存在则创建他们

1
2
MERGE (a:Person {name: 'Alice'})-[:FRIEND]->(b:Person {name: 'Bob'})
//如果Alice和Bob之间的Friend关系不存在,则创建他们

设置语句

1
2
MATCH (n:Person {name: 'Alice'}) SET n.age = 31 RETURN n
//将Alice的Person节点的age属性更新为31

删除语句

1
2
3
4
5
6
7
MATCH (n:Person {name: 'Alice'}) DELETE n
//删除名为Alice的节点
MATCH (a:Person)-[r:FRIEND]->(b:Person) WHERE a.name = 'Alice' AND b.name = 'Bob' DELETE r
//删除Alice和Bob之间的Friend关系

//带有关系的节点不能删,可以先删关系或者强制删除节点和关系
Match (n:Agency {name:"北京市昌平区新龙城"}) Detach Delete n

SDN(Spring Data Neo4j)

1. 添加依赖

首先,你需要在你的 Spring Boot 项目的 pom.xml(如果是 Maven 项目)或 build.gradle(如果是 Gradle 项目)中添加 Spring Data Neo4j 的依赖。

Maven 示例

1
2
3
4
5
6
7
8
<dependencies>  
<!-- Spring Boot Starter Data Neo4j -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-neo4j</artifactId>
</dependency>
<!-- 其他依赖 -->
</dependencies>

2. 配置 Neo4j

application.propertiesapplication.yml 文件中配置 Neo4j 数据库的连接信息。

1
2
3
4
5
6
spring:
neo4j:
authentication:
username: username
password: password
uri: 链接uri

3. 定义图实体和仓库

使用 Spring Data Neo4j 的注解来定义你的图实体和仓库接口。

实体类示例

1
2
3
4
5
6
7
8
9
10
11
import org.neo4j.springframework.data.core.schema.Id;  
import org.neo4j.springframework.data.core.schema.Node;

@Node //里面是在neo4j中的标签
public class Person {
@Id
private Long id;
private String name;

// 构造函数、getter 和 setter 省略
}

仓库接口示例

1
2
3
4
5
6
7
8
9
10
11
12
13
import org.neo4j.springframework.data.repository.Neo4jRepository;  

public interface PersonRepository extends Neo4jRepository<Person, Long> {

// 继承自Neo4jRepository的标准方法,如save、findAll等

// 自定义查询方法,通过方法命名约定
List<Person> findByName(String name);

// 使用@Query注解定义复杂的Cypher查询
@Query("MATCH (p:Person)-[:KNOWS]->(friend:Person) WHERE p.name = $name RETURN friend")
List<Person> findFriendsByName(String name);
}

4. 使用仓库

在你的服务层或控制器中注入仓库,并使用它来执行数据库操作。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
import org.springframework.beans.factory.annotation.Autowired;  
import org.springframework.stereotype.Service;

@Service
public class PersonService {

@Autowired
private PersonRepository personRepository;

public List<Person> findAllPersons() {
return personRepository.findAll();
}

// 其他业务逻辑
}