Python+Django+Scrapy构建游客行为分析可视化系统毕业设计指南

发布时间:2026/11/5 12:54:43

Python+Django+Scrapy构建游客行为分析可视化系统毕业设计指南 如果你正在为计算机毕业设计发愁不知道如何选择一个既有技术含量又能体现实际应用价值的课题那么游客行为分析可视化系统可能正是你需要的解决方案。这个项目不仅融合了Python全栈开发的核心技术更重要的是它解决了旅游行业对游客行为洞察的真实需求。传统的旅游数据分析往往停留在简单的统计报表层面而基于PythonDjangoScrapy的技术栈能够实现从数据采集、处理到可视化展示的完整闭环。这个项目的价值在于它不是一个纸上谈题的理论研究而是一个具备实际应用场景的完整系统。通过爬虫获取真实数据利用数据分析技术挖掘游客行为规律最终通过可视化界面直观呈现整个过程体现了现代数据驱动决策的技术理念。1. 项目核心价值与技术选型分析1.1 为什么选择游客行为分析作为毕业设计游客行为分析系统之所以适合作为计算机毕业设计主要基于以下几个关键因素技术综合性该项目涵盖了Web开发、数据爬取、数据处理、数据分析和可视化等多个技术领域能够全面展示你的技术能力。从技术栈角度看你需要掌握Django框架用于构建Web应用和API接口Scrapy框架用于数据采集和爬虫开发Pandas、NumPy用于数据清洗和分析ECharts、Matplotlib用于数据可视化数据库设计和管理MySQL/PostgreSQL实际应用价值随着旅游业的发展景区管理部门迫切需要了解游客的行为模式包括游览路线偏好、停留时间分布、消费习惯等。你的系统能够为景区运营提供数据支持这种实际应用背景会让答辩老师印象深刻。数据可得性通过网络爬虫可以相对容易地获取游客评价、景区信息等公开数据避免了数据采集的困难。同时你也可以使用模拟数据来演示系统功能。1.2 技术栈选择背后的考量Django vs Flask虽然Flask更轻量但Django提供了完整的MVC架构、ORM、Admin后台等开箱即用的功能更适合毕业设计这种需要快速构建完整系统的场景。Django的自带功能可以节省大量开发时间让你更专注于核心业务逻辑。Scrapy的优势相比RequestsBeautifulSoup的组合Scrapy提供了完整的爬虫框架包括调度器、下载器、管道等组件更适合大规模、结构化的数据采集。对于游客行为分析往往需要从多个网站采集数据Scrapy的框架特性正好满足这一需求。可视化方案选择ECharts作为前端可视化库与Django模板系统集成简单且提供了丰富的图表类型。对于需要复杂交互的可视化需求也可以考虑PyEcharts或Plotly与Django的集成方案。2. 系统架构设计与技术原理2.1 整体系统架构一个完整的游客行为分析系统通常采用分层架构设计数据采集层Scrapy → 数据存储层MySQL → 业务逻辑层Django → 展示层前端可视化数据流说明Scrapy爬虫从旅游网站、社交媒体等数据源采集游客相关数据清洗后的数据存储到MySQL数据库中Django处理业务逻辑提供REST API和数据查询服务前端页面通过图表库展示分析结果2.2 核心模块功能划分用户管理模块实现用户注册登录、权限管理等功能使用Django自带的认证系统可以快速实现。数据采集模块基于Scrapy框架负责从目标网站采集游客评论、景区信息、游客轨迹等数据。数据分析模块使用Pandas进行数据清洗和统计分析识别游客行为模式。可视化展示模块将分析结果通过图表形式展示支持多种维度的数据钻取。3. 开发环境准备与配置3.1 基础环境搭建首先确保你的开发环境满足以下要求# 检查Python版本 python --version # Python 3.8或以上版本 # 创建虚拟环境 python -m venv tourist_analysis source tourist_analysis/bin/activate # Linux/Mac # 或 tourist_analysis\Scripts\activate # Windows3.2 依赖包安装创建requirements.txt文件包含项目所需的主要依赖Django4.2.0 scrapy2.8.0 pandas1.5.0 numpy1.23.0 requests2.28.0 beautifulsoup44.11.0 mysqlclient2.1.0 django-rest-framework3.14.0 pyecharts1.9.1 matplotlib3.6.0 selenium4.8.0安装依赖pip install -r requirements.txt3.3 数据库配置在Django项目的settings.py中配置MySQL数据库# settings.py DATABASES { default: { ENGINE: django.db.backends.mysql, NAME: tourist_analysis, USER: your_username, PASSWORD: your_password, HOST: localhost, PORT: 3306, } }4. Django项目基础搭建4.1 创建Django项目和应用# 创建Django项目 django-admin startproject tourist_analysis_system cd tourist_analysis_system # 创建各个功能模块的应用 python manage.py startapp user_management python manage.py startapp data_collection python manage.py startapp data_analysis python manage.py startapp visualization4.2 项目目录结构规划合理的目录结构是项目成功的基础tourist_analysis_system/ ├── manage.py ├── tourist_analysis_system/ │ ├── __init__.py │ ├── settings.py │ ├── urls.py │ └── wsgi.py ├── user_management/ # 用户管理模块 ├── data_collection/ # 数据采集模块 ├── data_analysis/ # 数据分析模块 ├── visualization/ # 可视化模块 ├── static/ # 静态文件 │ ├── css/ │ ├── js/ │ └── images/ ├── templates/ # 模板文件 └── requirements.txt4.3 基础配置和路由设置在主urls.py中配置项目路由# tourist_analysis_system/urls.py from django.contrib import admin from django.urls import path, include from django.conf import settings from django.conf.urls.static import static urlpatterns [ path(admin/, admin.site.urls), path(user/, include(user_management.urls)), path(data/, include(data_collection.urls)), path(analysis/, include(data_analysis.urls)), path(visual/, include(visualization.urls)), ] static(settings.STATIC_URL, document_rootsettings.STATIC_ROOT)5. Scrapy爬虫开发实战5.1 创建Scrapy爬虫项目# 在Django项目根目录下创建爬虫项目 scrapy startproject tourist_spider cd tourist_spider scrapy genspider travel_site example.com5.2 爬虫核心代码实现以采集游客评论数据为例# tourist_spider/spiders/travel_site.py import scrapy import json from datetime import datetime class TravelSiteSpider(scrapy.Spider): name travel_site allowed_domains [example.com] start_urls [http://example.com/travel/reviews] def parse(self, response): # 解析列表页获取详情页链接 review_links response.css(.review-list a::attr(href)).getall() for link in review_links: yield response.follow(link, self.parse_review) # 处理分页 next_page response.css(.next-page::attr(href)).get() if next_page: yield response.follow(next_page, self.parse) def parse_review(self, response): # 解析详情页数据 item { source: self.name, crawl_time: datetime.now().strftime(%Y-%m-%d %H:%M:%S), scenic_spot: response.css(.spot-name::text).get(), user_name: response.css(.user-info .name::text).get(), review_content: response.css(.review-content::text).get(), rating: response.css(.rating::attr(data-score)).get(), visit_date: response.css(.visit-date::text).get(), helpful_count: response.css(.helpful-count::text).get(), } yield item5.3 数据存储管道将爬取的数据存储到MySQL数据库# tourist_spider/pipelines.py import MySQLdb from tourist_spider.items import ReviewItem class MySQLPipeline: def __init__(self, mysql_settings): self.mysql_settings mysql_settings classmethod def from_crawler(cls, crawler): return cls( mysql_settingscrawler.settings.get(MYSQL_SETTINGS) ) def open_spider(self, spider): self.conn MySQLdb.connect(**self.mysql_settings) self.cursor self.conn.cursor() def close_spider(self, spider): self.conn.close() def process_item(self, item, spider): if isinstance(item, ReviewItem): sql INSERT INTO tourist_reviews (source, scenic_spot, user_name, review_content, rating, visit_date, helpful_count, crawl_time) VALUES (%s, %s, %s, %s, %s, %s, %s, %s) self.cursor.execute(sql, ( item[source], item[scenic_spot], item[user_name], item[review_content], item[rating], item[visit_date], item[helpful_count], item[crawl_time] )) self.conn.commit() return item6. 数据分析模块实现6.1 数据清洗与预处理使用Pandas进行数据清洗# data_analysis/utils/data_cleaner.py import pandas as pd import numpy as np import re class TouristDataCleaner: def __init__(self, data_path): self.df pd.read_csv(data_path) def clean_rating(self): 清洗评分数据 # 将评分转换为数值类型 self.df[rating] pd.to_numeric(self.df[rating], errorscoerce) # 处理缺失值 self.df[rating].fillna(self.df[rating].mean(), inplaceTrue) def extract_visit_season(self): 从访问日期提取季节信息 def get_season(date_str): if pd.isna(date_str): return 未知 month int(date_str.split(-)[1]) if month in [3, 4, 5]: return 春季 elif month in [6, 7, 8]: return 夏季 elif month in [9, 10, 11]: return 秋季 else: return 冬季 self.df[visit_season] self.df[visit_date].apply(get_season) def analyze_sentiment(self): 简单的情感分析 positive_words [好, 不错, 推荐, 满意, 漂亮, 方便] negative_words [差, 不好, 不推荐, 失望, 脏, 贵] def get_sentiment(text): if pd.isna(text): return 中性 positive_count sum(1 for word in positive_words if word in text) negative_count sum(1 for word in negative_words if word in text) if positive_count negative_count: return 积极 elif negative_count positive_count: return 消极 else: return 中性 self.df[sentiment] self.df[review_content].apply(get_sentiment) def get_clean_data(self): 执行完整的清洗流程 self.clean_rating() self.extract_visit_season() self.analyze_sentiment() return self.df6.2 游客行为模式分析# data_analysis/utils/behavior_analyzer.py import pandas as pd from collections import Counter class TouristBehaviorAnalyzer: def __init__(self, clean_df): self.df clean_df def analyze_seasonal_trends(self): 分析季节性趋势 seasonal_stats self.df.groupby(visit_season).agg({ rating: [mean, count], helpful_count: mean }).round(2) return seasonal_stats def analyze_sentiment_distribution(self): 分析情感分布 sentiment_dist self.df[sentiment].value_counts(normalizeTrue) * 100 return sentiment_dist def find_popular_spots(self, top_n10): 找出最受欢迎的景区 spot_ratings self.df.groupby(scenic_spot).agg({ rating: mean, user_name: count }).round(2) spot_ratings.columns [avg_rating, review_count] return spot_ratings.nlargest(top_n, avg_rating) def analyze_rating_patterns(self): 分析评分模式 rating_patterns { rating_distribution: self.df[rating].value_counts().sort_index(), rating_vs_helpful: self.df.groupby(rating)[helpful_count].mean(), rating_vs_sentiment: pd.crosstab(self.df[rating], self.df[sentiment]) } return rating_patterns7. Django可视化接口开发7.1 视图函数和API设计# visualization/views.py from django.shortcuts import render from django.http import JsonResponse from data_analysis.utils.behavior_analyzer import TouristBehaviorAnalyzer import pandas as pd def dashboard(request): 主仪表板视图 return render(request, visualization/dashboard.html) def seasonal_trends_api(request): 季节性趋势数据API df pd.read_csv(cleaned_tourist_data.csv) analyzer TouristBehaviorAnalyzer(df) trends_data analyzer.analyze_seasonal_trends() # 转换为前端需要的格式 result { seasons: trends_data.index.tolist(), avg_ratings: trends_data[(rating, mean)].tolist(), review_counts: trends_data[(rating, count)].tolist() } return JsonResponse(result) def sentiment_analysis_api(request): 情感分析数据API df pd.read_csv(cleaned_tourist_data.csv) analyzer TouristBehaviorAnalyzer(df) sentiment_data analyzer.analyze_sentiment_distribution() result { sentiments: sentiment_data.index.tolist(), percentages: sentiment_data.tolist() } return JsonResponse(result)7.2 前端可视化实现使用ECharts实现交互式图表!-- templates/visualization/dashboard.html -- !DOCTYPE html html head meta charsetutf-8 title游客行为分析系统/title script srchttps://cdn.jsdelivr.net/npm/echarts5.4.0/dist/echarts.min.js/script style .chart-container { width: 100%; height: 400px; margin: 20px 0; } /style /head body div classcontainer h1游客行为分析仪表板/h1 div classchart-container idseasonalChart/div div classchart-container idsentimentChart/div div classchart-container idratingChart/div /div script // 初始化图表 var seasonalChart echarts.init(document.getElementById(seasonalChart)); var sentimentChart echarts.init(document.getElementById(sentimentChart)); // 季节性趋势图表 fetch(/visual/api/seasonal-trends/) .then(response response.json()) .then(data { var option { title: { text: 各季节游客评分趋势 }, tooltip: {}, xAxis: { data: data.seasons }, yAxis: {}, series: [{ name: 平均评分, type: line, data: data.avg_ratings }] }; seasonalChart.setOption(option); }); // 情感分析饼图 fetch(/visual/api/sentiment-analysis/) .then(response response.json()) .then(data { var option { title: { text: 游客评论情感分布 }, tooltip: { trigger: item }, series: [{ type: pie, data: data.sentiments.map((sentiment, index) { return { value: data.percentages[index], name: sentiment }; }) }] }; sentimentChart.setOption(option); }); /script /body /html8. 系统集成与数据流程测试8.1 完整数据流程验证为了确保系统各个模块能够协同工作需要设计完整的测试流程# integration_test.py import os import django import pandas as pd from scrapy.crawler import CrawlerProcess from tourist_spider.spiders.travel_site import TravelSiteSpider # 设置Django环境 os.environ.setdefault(DJANGO_SETTINGS_MODULE, tourist_analysis_system.settings) django.setup() def test_complete_workflow(): 测试完整的数据流程 # 1. 运行爬虫采集数据 print(开始数据采集...) process CrawlerProcess({ USER_AGENT: Mozilla/5.0, CONCURRENT_REQUESTS: 2, DOWNLOAD_DELAY: 1, }) process.crawl(TravelSiteSpider) process.start() # 2. 数据清洗和分析 print(开始数据清洗和分析...) from data_analysis.utils.data_cleaner import TouristDataCleaner from data_analysis.utils.behavior_analyzer import TouristBehaviorAnalyzer cleaner TouristDataCleaner(raw_tourist_data.csv) clean_df cleaner.get_clean_data() clean_df.to_csv(cleaned_tourist_data.csv, indexFalse) analyzer TouristBehaviorAnalyzer(clean_df) trends analyzer.analyze_seasonal_trends() sentiment analyzer.analyze_sentiment_distribution() print(季节性趋势分析结果:) print(trends) print(\n情感分布分析结果:) print(sentiment) # 3. 启动Django开发服务器进行可视化验证 print(数据流程测试完成可以启动Django服务器查看可视化结果) if __name__ __main__: test_complete_workflow()8.2 自动化数据更新机制实现定时数据更新确保系统数据的时效性# data_collection/management/commands/update_tourist_data.py from django.core.management.base import BaseCommand from scrapy.crawler import CrawlerProcess from tourist_spider.spiders.travel_site import TravelSiteSpider import schedule import time import threading class Command(BaseCommand): help 定时更新游客数据 def add_arguments(self, parser): parser.add_argument( --interval, typeint, default24, help数据更新间隔小时 ) def handle(self, *args, **options): def run_spider(): process CrawlerProcess() process.crawl(TravelSiteSpider) process.start() def scheduled_task(): schedule.every(options[interval]).hours.do(run_spider) while True: schedule.run_pending() time.sleep(1) # 在后台线程中运行定时任务 thread threading.Thread(targetscheduled_task) thread.daemon True thread.start() self.stdout.write( self.style.SUCCESS( f已启动定时数据更新任务每{options[interval]}小时执行一次 ) )9. 常见问题与解决方案9.1 爬虫开发中的常见问题反爬虫机制应对# 在Scrapy配置中添加反爬虫策略 custom_settings { DOWNLOAD_DELAY: 2, RANDOMIZE_DOWNLOAD_DELAY: True, CONCURRENT_REQUESTS_PER_DOMAIN: 1, USER_AGENT: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36, ROTATING_PROXY_LIST: [ proxy1.com:8000, proxy2.com:8000, ] }数据解析异常处理def parse_review(self, response): try: # 数据解析逻辑 item { scenic_spot: response.css(.spot-name::text).get() or 未知, # 其他字段... } # 数据验证 if not item[review_content]: self.logger.warning(f跳过空内容的评论: {response.url}) return yield item except Exception as e: self.logger.error(f解析错误: {e}, URL: {response.url})9.2 Django开发中的性能优化数据库查询优化# 避免N1查询问题 # 不推荐的写法 reviews Review.objects.all() for review in reviews: print(review.user.name) # 每次循环都会查询数据库 # 推荐的写法使用select_related reviews Review.objects.select_related(user).all() for review in reviews: print(review.user.name) # 一次性预加载关联数据分页处理大数据集from django.core.paginator import Paginator def paginate_large_dataset(request): all_reviews Review.objects.all() paginator Paginator(all_reviews, 50) # 每页50条 page_number request.GET.get(page) page_obj paginator.get_page(page_number) return render(request, reviews.html, {page_obj: page_obj})9.3 可视化性能优化数据聚合预处理# 对于大量数据的可视化预先进行数据聚合 def get_daily_visitor_stats(): 获取每日访客统计预聚合 from django.db.models import Count, Avg from django.utils import timezone from datetime import timedelta thirty_days_ago timezone.now() - timedelta(days30) stats Review.objects.filter( crawl_time__gtethirty_days_ago ).extra({ date: date(crawl_time) }).values(date).annotate( countCount(id), avg_ratingAvg(rating) ).order_by(date) return list(stats)10. 项目部署与生产环境配置10.1 生产环境部署准备使用Gunicorn部署Django# gunicorn.conf.py bind 0.0.0.0:8000 workers 3 worker_class sync worker_connections 1000 timeout 30 max_requests 1000 max_requests_jitter 100Nginx配置# /etc/nginx/sites-available/tourist_analysis server { listen 80; server_name your_domain.com; location /static/ { alias /path/to/your/static/files/; } location / { proxy_pass http://127.0.0.1:8000; proxy_set_header Host $host; proxy_set_header X-Real-IP $remote_addr; } }10.2 安全配置建议Django安全设置# settings.py 生产环境配置 DEBUG False ALLOWED_HOSTS [your_domain.com, localhost] # 安全中间件 MIDDLEWARE [ django.middleware.security.SecurityMiddleware, django.middleware.csrf.CsrfViewMiddleware, # 其他中间件... ] # 数据库密码等敏感信息使用环境变量 import os DATABASES { default: { ENGINE: django.db.backends.mysql, NAME: os.environ.get(DB_NAME), USER: os.environ.get(DB_USER), PASSWORD: os.environ.get(DB_PASSWORD), HOST: os.environ.get(DB_HOST), PORT: os.environ.get(DB_PORT, 3306), } }这个游客行为分析可视化项目不仅技术栈完整更重要的是它体现了从数据采集到价值呈现的完整数据科学流程。在毕业设计答辩时你可以重点展示系统的架构设计思路、数据处理流程、以及可视化分析结果的实际业务价值。建议在项目开发过程中注重代码规范编写清晰的文档这对毕业设计的评分会有很大帮助。同时考虑添加一些创新功能如实时数据更新、多维度分析对比等能够让你的项目在众多毕业设计中脱颖而出。
延伸阅读

更多相关文章

2026/10/30 23:30:28

Kafka与Spring Boot实现分布式事务的实践指南

1. 项目概述在微服务架构盛行的今天,分布式事务处理一直是开发者面临的棘手难题。当系统被拆分为多个独立服务后,传统的ACID事务难以跨越服务边界。而Kafka作为高吞吐量的分布式消息系统,结合Spring Boot的便捷开发特性,为我们提供…

2026/11/3 7:40:27

从JDK8升级到JDK17:性能优化与新特性实践

1. 为什么选择从JDK8升级到JDK17?作为一名长期使用JDK8的Java开发者,我最初对升级到JDK17也持观望态度。毕竟JDK8作为LTS版本已经稳定运行多年,大多数企业级应用和微服务都基于它构建。但经过深入调研和实际测试后,我发现升级到JD…

2026/11/5 12:29:32

Text to SQL系统第三层实现:复杂查询意图识别与优化

1. 项目概述Text to SQL系统作为自然语言处理与数据库技术交叉领域的重要应用,正在深刻改变着非技术人员与数据库交互的方式。这个看似简单的"输入问题,输出SQL"功能背后,隐藏着复杂的实现逻辑和技术挑战。今天我们就来拆解这个系统…

2026/11/5 12:29:32

Text-to-SQL系统架构解析与性能优化实践

1. 文本到SQL转换系统的核心价值 在数据驱动的时代,SQL作为与数据库交互的标准语言,其重要性不言而喻。但编写SQL查询需要专业技能,这成为了许多非技术用户获取数据的障碍。Text-to-SQL系统正是为解决这一痛点而生,它允许用户用自…

2026/11/5 12:29:32

钉钉办公自动化:OpenClaw Skill原理与应用

1. 项目概述 OpenClaw Skill是一个基于自动化原理设计的办公效率工具,专门针对钉钉平台的操作优化。它能模拟人工操作流程,实现消息自动收发、审批流程处理、考勤数据管理等高频办公场景的自动化。我在实际使用中发现,这个工具特别适合需要频…

2026/11/5 12:29:32

AI编程辅助工具:5个提升代码可用性的Prompt模板

1. 项目背景与核心价值 去年团队引入AI编程辅助工具时,我们经历了从"玩具demo"到"生产级应用"的艰难跨越。最深的体会是:需求沟通的质量直接决定了AI产出的可用性。那些模糊的"做个用户管理系统"之类的需求,AI…

2026/11/5 12:24:32

云原生智能体协同架构在城市轨道交通中的应用

1. 新一代城市轨道交通云原生智能体协同架构概述城市轨道交通作为现代都市的"大动脉",其运营效率和服务质量直接影响着千万市民的日常生活。近年来,随着云计算、人工智能等技术的快速发展,传统的轨道交通智能化系统架构正面临着前所…

2026/11/5 12:14:29

Stimulsoft Reports 2019.2.2 落地指南:老系统兼容与版本陷阱规避

简介:Stimulsoft Reports 2019.2.2 是一款面向.NET开发者的专业报表控件,适用于WinForms、ASP.NET及WPF平台,帮助开发者快速构建数据可视化报表与打印输出功能,尤其适合中高级C#工程师在企业级管理系统、BI看板或财务报表模块中集…

2026/11/4 12:38:23

面向复杂光照与角度的宠物面部识别鲁棒性增强策略

在智慧养宠时代,基于视觉的宠物身份识别技术正逐步从实验室走向家庭应用。然而,与配合度高的人类不同,宠物是典型的“非合作生物识别对象”——它们不会主动配合摄像头调整姿态,更无法控制光照环境。实际应用中,我们常…

2026/11/4 21:04:25

SSM电子书店源码全解析:结构、原理、部署与排错实战

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/11/5 0:02:07

多智能体协作系统架构设计与实践优化

1. 多智能体协作系统的时代背景2017年Transformer架构的诞生彻底改变了人工智能的发展轨迹。当行业还沉浸在单一大模型带来的性能突破时,Anthropic的研究团队已经将目光投向了更前沿的领域——如何让多个智能体通过协作产生超越单体能力的系统智能。这就像交响乐团中…

2026/11/5 0:02:07

大模型系统性入门实战指南:从原理到部署微调的全链路路线

提到大模型的系统性入门,我先说个结论:这事真不难,难的是资料太散、路线太多,今天这个框架明天那个工具,新人很容易在“收藏夹吃灰”和“教程看到一半放弃”之间反复横跳。市面上关于大模型的内容少说有几十万篇&#…

2026/11/5 0:02:07

鸿蒙文件系统沙箱机制解析与开发实践

1. 鸿蒙文件系统沙箱机制深度解析作为一名从Android转向鸿蒙开发的工程师,我深刻体会到文件系统访问是迁移过程中最先遇到的"拦路虎"。在Android上运行良好的文件读写代码,在鸿蒙真机环境却频频出现文件写入后神秘消失或直接抛出权限拒绝错误的…

2026/11/4 12:38:23

面向复杂光照与角度的宠物面部识别鲁棒性增强策略

在智慧养宠时代,基于视觉的宠物身份识别技术正逐步从实验室走向家庭应用。然而,与配合度高的人类不同,宠物是典型的“非合作生物识别对象”——它们不会主动配合摄像头调整姿态,更无法控制光照环境。实际应用中,我们常…

2026/11/4 21:04:25

SSM电子书店源码全解析:结构、原理、部署与排错实战

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

还想了解更多?直接咨询顾问

免费诊断 + 免费方案 + 透明报价。

全国咨询热线400-8866-253
免费获取方案
☎咨询二维码 ☎ ↑