Python: 实现数据可视化分析系统

后端基于Python 开源的 Web 框架 Flask,前端页面采用 LayUI 框架以及 Echarts 图表,数据库为sqlite。系统的功能模块分为数据采集和存储模块、数据处理和分析模块、可视化展示模块和系统管理模块。情感分析方面使用LDA等主题建模技术,结合领域特定词汇进行优化。有可视化大屏。

实现的结果如图所示:

项目工程目录:

具体实现步骤:

一、app.py 后端核心代码

app.py 后端核心代码

from flask import Flask, render_template, jsonify

import sqlite3

from collections import defaultdict

import jieba

import re

app = Flask(name)

自定义情感词典(示例)

sentiment_words = {

'好': 'positive', '不错': 'positive', '推荐': 'positive',

'差': 'negative', '难吃': 'negative', '投诉': 'negative'

}

数据库连接

def get_db():

conn = sqlite3.connect('reviews.db')

conn.row_factory = sqlite3.Row

return conn

情感分析函数

def analyze_sentiment(text):

positive = negative = 0

words = jieba.lcut(text)

for word in words:

if word in sentiment_words:

if sentiment_words[word] == 'positive':

positive += 1

else:

negative += 1

if positive > negative:

return 'positive'

elif negative > positive:

return 'negative'

else:

return 'neutral'

路由定义

@app.route('/')

def dashboard():

return render_template('dashboard.html')

情感分布数据接口

@app.route('/api/sentiment')

def sentiment_data():

conn = get_db()

cursor = conn.cursor()

cursor.execute('SELECT sentiment, COUNT(*) FROM reviews GROUP BY sentiment')

data = {row[0]: row[1] for row in cursor.fetchall()}

conn.close()

return jsonify(data)

评分分布接口

@app.route('/api/score_dist')

def score_dist():

conn = get_db()

cursor = conn.execute('''

SELECT score, COUNT(*) as count

FROM reviews

GROUP BY score ORDER BY score

''')

result = [{'score': row[0], 'count': row[1]} for row in cursor]

conn.close()

return jsonify(result)

分类统计接口

@app.route('/api/category_stats')

def category_stats():

conn = get_db()

cursor = conn.execute('''

SELECT category, COUNT(*) as count, AVG(score) as avg_score

FROM reviews

GROUP BY category

''')

result = [{

'category': row[0],

'count': row[1],

'avg_score': round(row[2], 1)

} for row in cursor]

conn.close()

return jsonify(result)

关键词提取接口

@app.route('/api/keywords/<type>')

def keywords(type):

conn = get_db()

cursor = conn.execute('SELECT content FROM reviews')

texts = [row[0] for row in cursor.fetchall()]

关键词提取逻辑

keywords = []

pattern = re.compile(r'服务|态度|热情' if type == 'service' else r'味道|口感|食材')

for text in texts:

words = jieba.lcut(text)

keywords.extend([w for w in words if pattern.search(w)])

统计词频

freq = defaultdict(int)

for word in keywords:

freq[word] += 1

return jsonify([{'name': k, 'value': v} for k, v in freq.items()])

if name == 'main':

app.run(debug=True)

二、前端代码

<!-- templates/dashboard.html 前端页面 -->

<!DOCTYPE html>

<html>

<head>

<meta charset="utf-8">

<title>数据可视化分析系统</title>

<link rel="stylesheet" href="/static/layui/css/layui.css">

<script src="/static/echarts.min.js"></script>

<script src="/static/layui/layui.js"></script>

</head>

<body>

<div class="layui-container">

<!-- 情感分布 -->

<div class="layui-row">

<div class="layui-col-md6">

<div id="sentimentChart" style="height:400px"></div>

</div>

<div class="layui-col-md6">

<div id="scoreChart" style="height:400px"></div>

</div>

</div>

<!-- 分类统计 -->

<div class="layui-row">

<div id="categoryChart" style="height:400px"></div>

</div>

<!-- 关键词云 -->

<div class="layui-row">

<div class="layui-col-md6">

<div id="serviceWordcloud" style="height:300px"></div>

</div>

<div class="layui-col-md6">

<div id="tasteWordcloud" style="height:300px"></div>

</div>

</div>

</div>

<script>

layui.use(function(){

const = layui.;

// 情感分布饼图

const sentimentChart = echarts.init(document.getElementById('sentimentChart'));

$.get('/api/sentiment', function(data){

sentimentChart.setOption({

title: { text: '评论情感分布' },

series: [{

type: 'pie',

data: Object.entries(data).map(([name, value]) => ({name, value}))

}]

});

});

// 评分分布直方图

const scoreChart = echarts.init(document.getElementById('scoreChart'));

$.get('/api/score_dist', function(data){

scoreChart.setOption({

title: { text: '评分分布' },

xAxis: { data: data.map(d => d.score) },

yAxis: { type: 'value' },

series: [{

type: 'bar',

data: data.map(d => d.count)

}]

});

});

// 分类统计柱状图

const categoryChart = echarts.init(document.getElementById('categoryChart'));

$.get('/api/category_stats', function(data){

categoryChart.setOption({

title: { text: '店铺分类统计' },

tooltip: { trigger: 'axis' },

xAxis: { data: data.map(d => d.category) },

yAxis: [{ type: 'value', name: '评论量' }],

series: [{

name: '评论量',

type: 'bar',

data: data.map(d => d.count)

}]

});

});

// 服务态度词云

const serviceWC = echarts.init(document.getElementById('serviceWordcloud'));

$.get('/api/keywords/service', function(data){

serviceWC.setOption({

title: { text: '服务态度关键词' },

series: [{

type: 'wordCloud',

data: data

}]

});

});

// 菜品口味词云

const tasteWC = echarts.init(document.getElementById('tasteWordcloud'));

$.get('/api/keywords/taste', function(data){

tasteWC.setOption({

title: { text: '菜品口味关键词' },

series: [{

type: 'wordCloud',

data: data

}]

});

});

});

</script>

</body>

</html>

三、系统运行说明:

  1. 需要安装的依赖:

bash

复制代码
pip install flask jieba
  1. 目录结构:
复制代码
├── app.py
├── templates
│   └── dashboard.html
└── static
    ├── layui
    │   ├── css
    │   └── js
    └── echarts.min.js

四、创建DB,插入数据:

复制代码
import sqlite3
from flask import jsonify

#insert data to DB.
def get_db():
    conn = sqlite3.connect('reviews.db')
    cursor = conn.cursor()
    # 创建表
    create_table_sql = """
        CREATE TABLE IF NOT EXISTS reviews (
            id INTEGER PRIMARY KEY,
            content TEXT,
            score INTEGER,
            category TEXT,
            region TEXT,
            sentiment TEXT
        );
        """
    cursor.execute(create_table_sql)
    conn.commit()  # 提交事务

    # 插入一些示例数据
    insert_data_sql = """
        INSERT INTO reviews (id,content, score, category, region, sentiment)
        VALUES 
        (1,'这家店的环境非常好,服务也很周到,菜品味道更是一流!', 5, '中餐', '北京', '正面'),
        (2,'菜品口味太一般了,没什么特色,价格还贵。', 2, '西餐', '上海', '负面');
        """
    cursor.execute(insert_data_sql)
    conn.commit()  # 提交事务
    cursor.execute('SELECT sentiment, COUNT(*) FROM reviews GROUP BY sentiment')
    data = {row[0]: row[1] for row in cursor.fetchall()}
    print("这是output: "+jsonify(data))
    conn.row_factory = sqlite3.Row
    return conn
def main():
    conn = get_db()
    cursor = conn.cursor()
    print("这是主函数的内容。")

if __name__ == "__main__":
    main()
相关推荐
喵手3 分钟前
Python爬虫实战:容器化与定时调度实战 - Docker + Cron + 日志轮转 + 失败重试完整方案(附CSV导出 + SQLite持久化存储)!
爬虫·python·爬虫实战·容器化·零基础python爬虫教学·csv导出·定时调度
2601_9491465323 分钟前
Python语音通知接口接入教程:开发者快速集成AI语音API的脚本实现
人工智能·python·语音识别
寻梦csdn44 分钟前
pycharm+miniconda兼容问题
ide·python·pycharm·conda
Java面试题总结2 小时前
基于 Java 的 PDF 文本水印实现方案(iText7 示例)
java·python·pdf
不懒不懒2 小时前
【决策树算法实战指南:从原理到Python实现】
python·决策树·id3·c4.5·catr
马猴烧酒.2 小时前
【面试八股|Java集合】Java集合常考面试题详解
java·开发语言·python·面试·八股
天空属于哈夫克32 小时前
Java 版:利用外部群 API 实现自动“技术开课”倒计时提醒
数据库·python·mysql
喵手2 小时前
Python爬虫实战:全站 Sitemap 自动发现 - 解析 sitemap.xml → 自动生成抓取队列的工业级实现!
爬虫·python·爬虫实战·零基础python爬虫教学·sitemap·解析sitemap.xml·自动生成抓取队列实现
luoluoal2 小时前
基于深度学习的web端多格式纠错系统(源码+文档)
python·mysql·django·毕业设计·源码
深蓝海拓2 小时前
PySide6从0开始学习的笔记(二十七) 日志管理
笔记·python·学习·pyqt