基于知识图谱的电影推荐系统——Neo4j&Python

这篇具有很好参考价值的文章主要介绍了基于知识图谱的电影推荐系统——Neo4j&Python。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

1. 数据解下载与配置

选择TMDB电影数据集,Netflix Prize 数据集下载。

也可直接从这里下载:链接: https://pan.baidu.com/s/1l6wjwcUzy5G_dIlVDbCkpw 提取码: pkq6 。

基于知识图谱的电影推荐系统——Neo4j&Python,推荐系统,知识图谱,知识图谱,neo4j,python

基于知识图谱的电影推荐系统——Neo4j&Python,推荐系统,知识图谱,知识图谱,neo4j,python

执行preproc.py文件,进行数据预处理,生成5个处理后的文件:

import pandas as pd
import json
import re

def Netflix(MAX_USER = 1000):
    d_movie = dict()
    s_movie = set()
    
    out_movies = open("../out_movies.csv","w")
    out_movies.write("title\n")

    for line in open("../movie_titles.csv","r",encoding = 'ISO-8859-1'):
        line = line.strip().split(',')
        movie_id = int(line[0])
        title = line[2].replace("\"","")
        title = "\"" + title + "\""
        
        d_movie[movie_id] = title
        
        if title in s_movie:
           continue
        s_movie.add(title)
        
        out_movies.write(f"{title}\n")
        
    out_movies.close()
    
    out_grade = open("../out_grade.csv","w")
    out_grade.write("user_id,title,grade\n")

    files = ["../combined_data_1.txt"]
    for f in files:
        movie_id = -1
        for line in open(f,"r"):
            pos = line.find(":")
            if pos != -1: # is a new user
                movie_id = int(line[:pos])
                continue
            line = line.strip().split(",")
            user_id = int(line[0])
            rating = int(line[1])
            
            if user_id > MAX_USER:
                continue

            out_grade.write(f"{user_id},{d_movie[movie_id]},{rating}\n")
            
    out_grade.close()

def TMDB():
    pattern = re.compile("[A-Za-z0-9]+")
    # 提取电影类型
    out_genre = open("../out_genre.csv","w",encoding='utf-8')
    out_genre.write("title,genre\n")
    # 提取电影关键词
    out_keyword = open("../out_keyword.csv","w",encoding='utf-8')
    out_keyword.write("title,keyword\n")
    # 提取电影制片人
    out_productor = open("../out_productor.csv","w",encoding='utf-8')
    out_productor.write("title,productor\n")
    
    df = pd.read_csv("../tmdb_5000_movies.csv", sep=",")
    json_columns = ['genres', 'keywords', 'production_companies']
    for column in json_columns:
        df[column] = df[column].apply(json.loads)
    df = df[["genres", "keywords", "original_title","production_companies"]]
    for _, row in df.iterrows():
        title = row["original_title"]
        if not pattern.fullmatch(title):
            continue
        title = "\"" + title + "\""
        for g in row["genres"]:
            genre = g["name"]
            genre = "\"" + genre + "\""
            out_genre.write(f"{title},{genre}\n")
        for g in row["keywords"]:
            keyword = g["name"]
            keyword = "\"" + keyword + "\""
            out_keyword.write(f"{title},{keyword}\n")
        for g in row["production_companies"]:
            productor = g["name"]
            productor = "\"" + productor + "\""
            out_productor.write(f"{title},{productor}\n")

    
if __name__ == "__main__":
    Netflix()
    TMDB()

基于知识图谱的电影推荐系统——Neo4j&Python,推荐系统,知识图谱,知识图谱,neo4j,python

2. 将处理好的数据导入数据库中

将上面数据预处理生成的5个文件,放入import文件夹中:

基于知识图谱的电影推荐系统——Neo4j&Python,推荐系统,知识图谱,知识图谱,neo4j,python

基于知识图谱的电影推荐系统——Neo4j&Python,推荐系统,知识图谱,知识图谱,neo4j,python

3. 执行项目

修改main.py中的driver,输入自己数据库的用户名与密码。

执行main.py文件:

from neo4j import GraphDatabase
import pandas as pd

uri = "neo4j://localhost:7687"
driver = GraphDatabase.driver(uri, auth=("neo4j", "Liu881389."))

k = 10 # nearest neighbors (most similar users) to consider
movies_common = 3 # how many movies in common to be consider an user similar
users_common = 2 # minimum number of similar users that have seen the movie to consider it
threshold_sim = 0.9 # threshold to consider users similar

def load_data():
    with driver.session() as session:
        session.run("""MATCH ()-[r]->() DELETE r""")
        session.run("""MATCH (r) DELETE r""")
        
        print("Loading movies...")
        #加载数据,创建Movie标签,title属性的实体
        session.run("""
            LOAD CSV WITH HEADERS FROM "file:///out_movies.csv" AS csv
            CREATE (:Movie {title: csv.title})
            """)
            
        print("Loading gradings...")
        #加载评分数据,MERGE是搜索给定模式,如果存在,则返回结果如果它不存在于图中,则它创建新的节点/关系并返回结果。
        session.run("""
            LOAD CSV WITH HEADERS FROM "file:///out_grade.csv" AS csv
            MERGE (m:Movie {title: csv.title}) 
            MERGE (u:User {id: toInteger(csv.user_id)})
            CREATE (u)-[:RATED {grading : toInteger(csv.grade)}]->(m)
            """)
        #加载影片类型数据    
        print("Loading genres...")
            
        session.run("""
            LOAD CSV WITH HEADERS FROM "file:///out_genre.csv" AS csv
            MERGE (m:Movie {title: csv.title})
            MERGE (g:Genre {genre: csv.genre})
            CREATE (m)-[:HAS_GENRE]->(g)
            """)
            
        print("Loading keywords...")
        #加载关键词数据    
        session.run("""
            LOAD CSV WITH HEADERS FROM "file:///out_keyword.csv" AS csv
            MERGE (m:Movie {title: csv.title})
            MERGE (k:Keyword {keyword: csv.keyword})
            CREATE (m)-[:HAS_KEYWORD]->(k)
            """)
            
        print("Loading productors...")
        #制片人    
        session.run("""
            LOAD CSV WITH HEADERS FROM "file:///out_productor.csv" AS csv
            MERGE (m:Movie {title: csv.title})
            MERGE (p:Productor {name: csv.productor})
            CREATE (m)-[:HAS_PRODUCTOR]->(p)
            """)

def queries():
    while True:
        userid = int(input("请输入要为哪位用户推荐电影,输入其ID即可: "))
        m = int(input("为该用户推荐多少个电影呢? "))
        
        genres = []
        if int(input("是否需要过滤掉不喜欢的类型?(输入0或1)")):#过滤掉不喜欢的类型
            with driver.session() as session:
                try:
                    q = session.run(f"""MATCH (g:Genre) RETURN g.genre AS genre""")
                    result = []
                    for i, r in enumerate(q):
                        result.append(r["genre"])#找到图谱中所有的电影类型
                    df = pd.DataFrame(result, columns=["genre"])
                    print()
                    print(df)
                    inp = input("输入不喜欢的类型索引即可,例如:1 2 3  ")
                    if len(inp) != 0:
                        inp = inp.split(" ")
                        genres = [df["genre"].iloc[int(x)] for x in inp]
                except:
                    print("Error")
                    
        with driver.session() as session:#找到当前ID评分的电影
            q = session.run(f"""
                    MATCH (u1:User {{id : {userid}}})-[r:RATED]-(m:Movie)
                    RETURN m.title AS title, r.grading AS grade
                    ORDER BY grade DESC
                    """)
            
            print()
            print("Your ratings are the following:")
            
            result = []
            for r in q:
                result.append([r["title"], r["grade"]])
                
            if len(result) == 0:
                print("No ratings found")
            else:
                df = pd.DataFrame(result, columns=["title", "grade"])
                print()
                print(df.to_string(index=False))
            print()
            
            session.run(f"""
                MATCH (u1:User)-[s:SIMILARITY]-(u2:User)
                DELETE s
                """)
            #找到当前用户评分的电影以及这些电影被其他用户评分的用户,with是把查询集合当做结果以便后面用where 余弦相似度计算
            session.run(f"""
                MATCH (u1:User {{id : {userid}}})-[r1:RATED]-(m:Movie)-[r2:RATED]-(u2:User)
                WITH
                    u1, u2,
                    COUNT(m) AS movies_common,
                    SUM(r1.grading * r2.grading)/(SQRT(SUM(r1.grading^2)) * SQRT(SUM(r2.grading^2))) AS sim
                WHERE movies_common >= {movies_common} AND sim > {threshold_sim}
                MERGE (u1)-[s:SIMILARITY]-(u2)
                SET s.sim = sim
                """)
                
            Q_GENRE = ""
            if (len(genres) > 0):
                Q_GENRE = "AND ((SIZE(gen) > 0) AND "
                Q_GENRE += "(ANY(x IN " + str(genres) + " WHERE x IN gen))"
                Q_GENRE += ")"
            #找到相似的用户,然后看他们喜欢什么电影 Collect:将所有值收集到一个集合list中
            q = session.run(f"""
                    MATCH (u1:User {{id : {userid}}})-[s:SIMILARITY]-(u2:User)
                    WITH u1, u2, s
                    ORDER BY s.sim DESC LIMIT {k}
                    MATCH (m:Movie)-[r:RATED]-(u2)
                    OPTIONAL MATCH (g:Genre)--(m)
                    WITH u1, u2, s, m, r, COLLECT(DISTINCT g.genre) AS gen
                    WHERE NOT((m)-[:RATED]-(u1)) {Q_GENRE}
                    WITH
                        m.title AS title,
                        SUM(r.grading * s.sim)/SUM(s.sim) AS grade,
                        COUNT(u2) AS num,
                        gen
                    WHERE num >= {users_common}
                    RETURN title, grade, num, gen
                    ORDER BY grade DESC, num DESC
                    LIMIT {m}
                    """)

            print("Recommended movies:")

            result = []
            for r in q:
                result.append([r["title"], r["grade"], r["num"], r["gen"]])
            if len(result) == 0:
                print("No recommendations found")
                print()
                continue
            df = pd.DataFrame(result, columns=["title", "avg grade", "num recommenders", "genres"])
            print()
            print(df.to_string(index=False))
            print()

if __name__ == "__main__":
    if int(input("是否需要重新加载并创建知识图谱?(请选择输入0或1)")):
        load_data()
    queries()

运行main.py文件后:

基于知识图谱的电影推荐系统——Neo4j&Python,推荐系统,知识图谱,知识图谱,neo4j,python

系统会询问是否需要重新加载并创建知识图谱,在第一次时输入1。

基于知识图谱的电影推荐系统——Neo4j&Python,推荐系统,知识图谱,知识图谱,neo4j,python

加载完成后可以在neo4j中查看:

基于知识图谱的电影推荐系统——Neo4j&Python,推荐系统,知识图谱,知识图谱,neo4j,python

接下来输入需要查询的信息:

基于知识图谱的电影推荐系统——Neo4j&Python,推荐系统,知识图谱,知识图谱,neo4j,python

输出结果:

基于知识图谱的电影推荐系统——Neo4j&Python,推荐系统,知识图谱,知识图谱,neo4j,python文章来源地址https://www.toymoban.com/news/detail-554942.html

到了这里,关于基于知识图谱的电影推荐系统——Neo4j&Python的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • Neo4j图数据库实践——基于知识图谱方法开发构建猪类养殖疾病问答查询系统

    Neo4j是一个开源的、高性能的图形数据库。它被设计用于存储、检索和处理具有复杂关系的大规模数据。与传统的关系型数据库不同,Neo4j使用图形结构来表示数据,其中节点表示实体,边表示实体之间的关系。这使得Neo4j在处理关系密集型数据时非常强大和高效。 以下是Ne

    2024年02月07日
    浏览(57)
  • 图数据库_Neo4j的使用场景_以及Windows版Neo4j Community Server安装_欺诈检测_推荐_知识图谱---Neo4j图数据库工作笔记0003

    可以看到使用场景,比如欺诈检测, 要建立图谱,才能进行,欺诈人员检测   可以看到图谱的各种应用场景 然后推荐引擎也需要,可以看到 在金融,旅行,求职招聘,保健,服务,媒体娱乐,都可以进行推荐   然后还有知识图谱 身份访问管理,这里,可以进行安全管理,可以挖掘出潜在关系

    2024年02月12日
    浏览(36)
  • 知识图谱实战应用9-基于neo4j的知识图谱框架设计与类模型构建

    大家好,我是微学AI,今天给大家介绍一下知识图谱实战应用9-基于neo4j的知识图谱框架设计与类模型构建。我将构建KnowledgeGraphs的类,用于操作Neo4j图数据库中的知识图谱数据。方便管理整个知识图谱操作。创建KnowledgeGraphs类可以使操作数据的代码更加模块化和可复用。使用

    2024年02月07日
    浏览(46)
  • Python neo4j建立知识图谱,药品知识图谱,neo4j知识图谱,知识图谱的建立过程,智能用药知识图谱,智能问诊必备知识图谱

    一、知识图谱概念 知识图谱的概念是由谷歌公司在2012年5月17日提出的,谷歌公司将以此为基础构建下一代智能化搜索引擎,知识图谱技术创造出一种全新的信息检索模式,为解决信息检索问题提供了新的思路。本质上,知识图谱是一种揭示实体之间关系的语义网络,可以对

    2024年01月17日
    浏览(46)
  • 【Neo4j与知识图谱】Neo4j的常用语法与一个简单知识图谱构建示例

    Neo4j是一种基于图形结构的NoSQL数据库,它采用了Cypher查询语言来查询和操作图形数据。下面是Neo4j中语法知识的详细总结和示例: 1.创建节点和关系 在Neo4j中,可以使用CREATE语句来创建节点和关系。下面是创建一个节点的示例: 这将创建一个标签为Person、属性为name和age的节

    2024年02月04日
    浏览(51)
  • 医疗知识图谱 neo4j

    开源项目: https://github.com/liuhuanyong/QASystemOnMedicalKG pip install pyahocorasick pip install py2neo 需要改的点: 1.改连接的方式 2.改读文件的方式 MedicalGraph 运行: build_medicalgraph.py 时间很长,几个小时 关闭neo4j客户端 导入文件 文件见网盘 1.首先通过ahocorasick提取出,属于哪种疾病

    2024年02月09日
    浏览(44)
  • Neo4j简单构建知识图谱实例

    目录  一、需要两组数据 二、提取所需专题数据 三、利用结巴分词将专题数据分词 四、连接并绘制知识图谱 五、消除重复节点及重复关系 六、结果展示 Ps:在使用Neo4j前,需要先在该安装路径文件下cmd运行,输入neo4j console 即可启动,可根据关闭时输入neo4j stop,如下图所示

    2023年04月12日
    浏览(52)
  • (知识图谱学习1)neo4j基础

    目录 一、neo4j安装与环境配置 官网:https://neo4j.com/download-center/ 下载社区版neo4j服务 neo4j环境变量配置 jdk下载 jdk版本: 启动neo4j 二、cypher语句基本增删改查 增 删除 改 查 三、Py2neo连接neo4j 安装pip install py2neo 连接neo4j 建立节点 建立关系 匹配节点 匹配关系 删除节点 删除关系

    2024年02月10日
    浏览(47)
  • 知识图谱构建: Neo4j 常见实例应用

    社交网络图:存储用户之间的关系和联系,如朋友关系、粉丝关系等。 产品推荐系统:利用用户的历史购买记录和评分数据,推荐相似的产品。 客户关系管理:存储企业和客户之间的联系,包括联系信息、交易记录等。 知识图谱:存储各种实体之间的关系,如人物、事件、

    2024年02月10日
    浏览(48)
  • 再相逢【知识图谱】中文医学知识图谱CMeKG,中文产科医学知识图谱COKG | 附:图数据库Neo4j下载安装教学(遇到问题并解决) + Neo4j基本操作

      无论结果如何,请相信那些你努力游向岸的日子都有它的意义。   🎯 作者主页 : 追光者♂ 🔥          🌸 个人简介 : 计算机专业硕士研究生 💖、 2022年CSDN博客之星人工智能领域TOP4 🌟、 阿里云社区特邀专家博主 🏅、 CSDN-人工智能领域新星创作者 🏆、 预期20

    2024年02月14日
    浏览(70)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包