MySQL数据库基础练习系列:科研项目管理系统

news2024/11/17 11:32:04

DDL

CREATE TABLE Users (
    user_id INT AUTO_INCREMENT PRIMARY KEY COMMENT '用户ID',
    username VARCHAR(50) NOT NULL UNIQUE COMMENT '用户名',
    password VARCHAR(255) NOT NULL COMMENT '密码',
    gender ENUM('男', '女') NOT NULL COMMENT '性别',
    email VARCHAR(100) UNIQUE COMMENT '邮箱'
);
 
CREATE TABLE Roles (
    role_id INT AUTO_INCREMENT PRIMARY KEY COMMENT '角色ID',
    role_name VARCHAR(50) NOT NULL UNIQUE COMMENT '角色名称'
);
 
CREATE TABLE UserRoles (
    user_id INT COMMENT '用户ID',
    role_id INT COMMENT '角色ID',
    PRIMARY KEY (user_id, role_id),
    FOREIGN KEY (user_id) REFERENCES Users(user_id),
    FOREIGN KEY (role_id) REFERENCES Roles(role_id)
);
 
CREATE TABLE Projects (
    project_id INT AUTO_INCREMENT PRIMARY KEY COMMENT '项目ID',
    project_name VARCHAR(100) NOT NULL COMMENT '项目名称',
    project_description TEXT COMMENT '项目描述',
    principal_investigator_id INT COMMENT '主研人ID',
    start_date DATE NOT NULL COMMENT '开始日期',
    end_date DATE NOT NULL COMMENT '结束日期',
    status ENUM('申请中', '审批中', '执行中', '结题') NOT NULL COMMENT '项目状态',
    FOREIGN KEY (principal_investigator_id) REFERENCES Users(user_id)
);
 
CREATE TABLE Funds (
    fund_id INT AUTO_INCREMENT PRIMARY KEY COMMENT '资金ID',
    project_id INT NOT NULL COMMENT '项目ID',
    source VARCHAR(100) NOT NULL COMMENT '资金来源',
    amount DECIMAL(10, 2) NOT NULL COMMENT '资金金额',
    FOREIGN KEY (project_id) REFERENCES Projects(project_id)
);
 
CREATE TABLE Achievements (
    achievement_id INT AUTO_INCREMENT PRIMARY KEY COMMENT '成果ID',
    project_id INT NOT NULL COMMENT '项目ID',
    achievement_name VARCHAR(100) NOT NULL COMMENT '成果名称',
    achievement_type ENUM('论文', '专利', '获奖', '其他') NOT NULL COMMENT '成果类型',
    description TEXT COMMENT '成果描述',
    FOREIGN KEY (project_id) REFERENCES Projects(project_id)
);
 
CREATE TABLE ProjectLogs (
    log_id INT AUTO_INCREMENT PRIMARY KEY COMMENT '日志ID',
    project_id INT NOT NULL COMMENT '项目ID',
    user_id INT NOT NULL COMMENT '用户ID',
    log_date DATETIME NOT NULL COMMENT '日志日期',
    log_content TEXT NOT NULL COMMENT '日志内容',
    FOREIGN KEY (project_id) REFERENCES Projects(project_id),
    FOREIGN KEY (user_id) REFERENCES Users(user_id)
);

DML

INSERT INTO Roles (role_name) VALUES
('管理员'),
('项目负责人'),
('项目成员');
INSERT INTO Users (username, password, gender, email) VALUES
('诸葛亮', '123', '男', 'zhugeliang@example.com'),
('孙悟空', '123', '男', 'sunwukong@example.com'),
('林黛玉', '123', '女', 'lindaiyu@example.com');
INSERT INTO UserRoles (user_id, role_id) VALUES
(1, 1), -- 诸葛亮是管理员
(2, 2), -- 孙悟空是项目负责人
(2, 3), -- 孙悟空也是项目成员
(3, 3);  -- 林黛玉是项目成员
INSERT INTO Projects (project_name, project_description, principal_investigator_id, start_date, end_date, status) VALUES
('三国历史研究项目', '研究三国历史背景', 1, '2023-01-01', '2023-12-31', '执行中'),
('西游记文化研究', '探究西游记的文学价值', 2, '2023-02-01', '2024-01-31', '申请中'),
('红楼梦解读', '分析红楼梦的深层含义', 2, '2023-03-01', '2023-11-30', '审批中');
INSERT INTO Funds (project_id, source, amount) VALUES
(1, '国家社会科学基金', 50000.00),
(2, '企业赞助', 30000.00),
(3, '学校科研基金', 45000.00),
(1, '地方政府资助', 20000.00); -- 同一个项目可以有多个经费来源
INSERT INTO Achievements (project_id, achievement_name, achievement_type, description) VALUES
(1, '三国历史研究报告', '论文', '详细分析了三国时期的历史事件'),
(2, '西游记文化解读', '论文', '深入探讨了西游记的文化内涵'),
(3, '红楼梦人物分析', '论文', '对红楼梦中的主要人物进行了深入剖析'),
(2, '西游记新发现', '专利', '发现了西游记中的新文学元素'); -- 同一个项目可以有多个成果
INSERT INTO ProjectLogs (project_id, user_id, log_date, log_content) VALUES
(1, 1, '2023-01-10 10:00:00', '项目启动会议召开'),
(2, 2, '2023-02-15 15:30:00', '提交项目申请书至学院'),
(3, 3, '2023-03-20 09:45:00', '开始收集红楼梦相关资料'),
(1, 1, '2023-04-01 14:15:00', '第一阶段研究成果汇报');

ER图 

 ER图

 模型图

简单查询

一、查询用户信息,仅显示用户的姓名与项目名称,用中文显示列名

SELECT DISTINCT
    u.username AS 用户名,
    p.project_name AS 项目名称
FROM
    Users u
JOIN
    Projects p ON u.user_id = p.principal_investigator_id;

二、根据项目名称进行模糊查询,模糊查询要进行索引,需要给出explain语句

EXPLAIN SELECT project_id, project_name
FROM Projects
WHERE project_name LIKE '%三国%';

三、统计用户的项目信息,查询所有用户的项目数量,并进行倒序排列

SELECT 
    u.username AS 用户名,
    COUNT(p.project_id) AS 项目数量
FROM 
    Users u
LEFT JOIN 
    Projects p ON u.user_id = p.principal_investigator_id
GROUP BY 
    u.user_id, u.username
ORDER BY 
    项目数量 DESC;

复杂查询

一、查询用户的基本信息,项目信息

SELECT 
    u.user_id,
    u.username,
    u.gender,
    u.email,
    p.project_id,
    p.project_name,
    p.project_description,
    p.start_date,
    p.end_date,
    p.status
FROM 
    Users u
LEFT JOIN 
    Projects p ON u.user_id = p.principal_investigator_id;

二、查看项目中项目阶段最多的项目对应的类型

SELECT 
    p.project_name,
    p.status
FROM 
    Projects p
WHERE 
    (SELECT COUNT(*) 
     FROM Projects p2 
     WHERE p2.status = p.status) = 
    (SELECT MAX(cnt) 
     FROM (SELECT status, COUNT(*) as cnt 
           FROM Projects 
           GROUP BY status) as subquery);

三、查询项目最多的用户,并且查询用户的全部信息与当前项目阶段

SET @MostProjectsUserId = (
    SELECT principal_investigator_id
    FROM Projects
    GROUP BY principal_investigator_id
    ORDER BY COUNT(*) DESC
    LIMIT 1
);

SELECT 
    u.*,
    p.project_id,
    p.project_name,
    p.status AS current_project_status
FROM 
    Users u
JOIN 
    Projects p ON u.user_id = p.principal_investigator_id
WHERE 
    u.user_id = @MostProjectsUserId;

触发器

触发器一:项目状态更新时记录日志

DELIMITER $$
CREATE TRIGGER trg_after_project_status_update
AFTER UPDATE ON Projects
FOR EACH ROW
BEGIN
    IF NEW.status <> OLD.status THEN
        INSERT INTO ProjectLogs (project_id, user_id, log_date, log_content)
        VALUES (NEW.project_id, @CURRENT_USER_ID, NOW(), '项目状态已更新');
    END IF;
END;
$$
DELIMITER ;

触发器二:用户角色变更时记录日志

DELIMITER $$
CREATE TRIGGER trg_after_fund_insert
AFTER INSERT ON Funds
FOR EACH ROW
BEGIN
    INSERT INTO ProjectLogs (project_id, user_id, log_date, log_content)
    VALUES (NEW.project_id, @CURRENT_USER_ID, NOW(), CONCAT('项目获得资金:', NEW.source, ',金额为:', NEW.amount));
END;
$$
DELIMITER ;

触发器三:用户角色变更时记录日志

CREATE TABLE UserRoleLogs (
    log_id INT AUTO_INCREMENT PRIMARY KEY COMMENT '日志ID',
    user_id INT NOT NULL COMMENT '用户ID',
    old_role_id INT COMMENT '旧角色ID',
    new_role_id INT COMMENT '新角色ID',
    log_date DATETIME NOT NULL COMMENT '日志日期',
    log_content TEXT COMMENT '日志内容',
    FOREIGN KEY (user_id) REFERENCES Users(user_id),
    FOREIGN KEY (old_role_id) REFERENCES Roles(role_id),
    FOREIGN KEY (new_role_id) REFERENCES Roles(role_id)
);

DELIMITER $$
CREATE TRIGGER trg_after_user_role_change
AFTER INSERT ON UserRoles
FOR EACH ROW
BEGIN
    DECLARE old_role_name VARCHAR(50);
    DECLARE new_role_name VARCHAR(50);
    SELECT role_name INTO new_role_name FROM Roles WHERE role_id = NEW.role_id;
    IF new_role_name IS NOT NULL THEN
        INSERT INTO UserRoleLogs (user_id, new_role_id, log_date, log_content)
        VALUES (NEW.user_id, NEW.role_id, NOW(), CONCAT('用户', NEW.user_id, '被赋予了新角色:', new_role_name));
    END IF;
END;
$$
DELIMITER ;

存储过程 

存储过程 1: 分配用户角色

DELIMITER $$
CREATE PROCEDURE AssignUserRole(IN userId INT, IN roleName VARCHAR(50))
BEGIN
    DECLARE roleId INT;
    DECLARE CONTINUE HANDLER FOR NOT FOUND SET @errorMsg = 'Role not found.';
    SELECT role_id INTO roleId FROM Roles WHERE role_name = roleName;
    IF roleId IS NULL THEN
        SIGNAL SQLSTATE '45000' SET MESSAGE_TEXT = @errorMsg;
    END IF;
    IF NOT EXISTS (SELECT 1 FROM UserRoles WHERE user_id = userId AND role_id = roleId) THEN
        INSERT INTO UserRoles (user_id, role_id) VALUES (userId, roleId);
    END IF;
    SELECT 'Role assigned successfully.' AS message;
END $$
DELIMITER ;

存储过程 2: 更新项目状态并记录日志

DELIMITER $$
CREATE PROCEDURE UpdateProjectStatus(IN projectId INT, IN newStatus ENUM('申请中', '审批中', '执行中', '结题'))
BEGIN
    DECLARE OLD_STATUS ENUM('申请中', '审批中', '执行中', '结题');
    SELECT status INTO OLD_STATUS FROM Projects WHERE project_id = projectId;
    UPDATE Projects SET status = newStatus WHERE project_id = projectId;
    INSERT INTO ProjectLogs (project_id, user_id, log_date, log_content)
    VALUES (projectId, USER(), NOW(), CONCAT('Project status changed from ', OLD_STATUS, ' to ', newStatus));
    SELECT 'Project status updated successfully.' AS message;
END $$
DELIMITER ;

存储过程 3: 分配项目资金并检查预算

ALTER TABLE Projects ADD total_budget DECIMAL(10, 2) NOT NULL DEFAULT 0 COMMENT '项目总预算';
DELIMITER $$
CREATE PROCEDURE AllocateProjectFunds(
    IN p_project_id INT,
    IN p_source VARCHAR(100),
    IN p_amount DECIMAL(10, 2)
)
BEGIN
    DECLARE v_total_budget DECIMAL(10, 2);
    DECLARE v_allocated_funds DECIMAL(10, 2);
    SELECT total_budget INTO v_total_budget FROM Projects WHERE project_id = p_project_id;
    SELECT SUM(amount) INTO v_allocated_funds FROM Funds WHERE project_id = p_project_id;
    IF v_total_budget >= (v_allocated_funds + p_amount) THEN
        INSERT INTO Funds (project_id, source, amount) VALUES (p_project_id, p_source, p_amount);
        INSERT INTO ProjectLogs (project_id, user_id, log_date, log_content)
        VALUES (p_project_id, USER(), NOW(),CONCAT('资金已成功分配给项目', p_project_id, ',金额:', p_amount, ',来源:', p_source));
        SELECT '资金分配成功' AS message;
    ELSE
        SELECT '预算不足,无法分配资金' AS message;
    END IF;
END $$
DELIMITER ;

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1868072.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

Linux系统iptables应用SNAT和DNAT

一、SNAT 1.SNAT应用环境 局域网主机共享单个公网IP地址接入Internet (私有IP不能在Internet中正常路由) 2.SNAT原理 源地址转换&#xff0c;根据指定条件修改数据包的源IP地址&#xff0c;通常被叫做源映谢 数据包从内网发送到公网时&#xff0c;SNAT会把数据包的源IP由私…

AI产品打造全攻略:看我是如何预测用户流失,搞定AI产品全流程的

前言 对于任何互联网公司而言&#xff0c;用户流失无疑是一个不容忽视的问题。在本文中&#xff0c;我将通过一个真实的预测用户流失的项目案例&#xff0c;带领大家深入了解AI产品从筹备到上线的整个流程。这个过程将展现AI产品经理的工作全貌&#xff0c;包括各个环节的角色…

汇编语言作业(十一)

目录 一、实验目的 二、实验内容 三&#xff0e;实验步骤以及结果 1、编译器换用vscode&#xff0c;但我现在只能把vscode当成代码编辑器来用&#xff0c;运行、调试都不成功。 2、本文是参考这份博客写的代码&#xff1a; 四、实验结果与分析 五&#xff0e;实验总结 一…

【AI绘画SD】解锁AIGC写实摄影要素:摄影构图与视角关键提示,SD3模型最新体验

大家好我是安琪&#xff01; 摄影构图与角度介绍 在现实摄影领域中&#xff0c;创作出优秀的摄影图像会涉及很多关键技术要素&#xff0c;如&#xff1a;光影效果、摄影构图&#xff08;摄影机位置&#xff1a;相机与主体的距离&#xff09;和摄影角度&#xff08;相机相对于…

下拉选择输入框(基于elment-ui)

最近在需求中&#xff0c;需要有一个下拉选择功能&#xff0c;又得可以输入&#xff0c;在 element-ui 官网找了&#xff0c;发现没有适合的&#xff0c;然后在修炼 cv 大法的我&#xff0c;也在网上看了一下&#xff0c;但是也都感觉不合适&#xff0c;所以就自己写了一个&…

nuxt3项目打包后获取.env设置的环境变量无效的解决办法

问题描述 在nuxt3项目开发过程中&#xff0c;设置了开发环境变量和生产环境变量&#xff0c;在本地开发时都能正常获取&#xff0c;但打包部署时获取不到&#xff0c;设置如下&#xff1a; //.env.development文件示例 SERVER_API_PATHhttp://192.168.25.100//.env.productio…

从挑战到实战!TDengine 新能源行业研讨会要点回顾

近年来&#xff0c;随着全球对可再生能源需求的不断增长&#xff0c;新能源行业迎来了前所未有的发展机遇。然而&#xff0c;伴随着行业的快速发展&#xff0c;海量数据的管理和高效利用成为了行业面临的重要挑战。如何通过先进的数据管理技术提升新能源系统的效率和可靠性&…

Qt开发 | Qmake与CMake | Qt窗口基类 | VS Qt项目与QtCreator项目相互转化 | Qt架构 | Qt学习方法

文章目录 一、Qmake与CMake介绍1.Qmake2.CMake3.使用qmake还是cmake&#xff1f; 二、Qt3个窗口基类的区别三、vs qt与QtCreator项目相互转化方法1.QtCreator项目转VS Qt2.VS Qt项目转QtCreator项目 四、Qt架构介绍与学习方法详解 一、Qmake与CMake介绍 Qmake和CMake都是构建系…

iOS项目开发遇到问题杂项坑点记录

ios17 弹窗UIAlertController展示逻辑变化&#xff0c;单个词一行展示不下不换行&#xff08;这前版本会换行&#xff09;&#xff0c;直接截断超出部分。 UINavigationController push立刻pop会异常&#xff0c;使用用setViewCollerllers可以避免这个问题 键盘切换后立刻切页…

【java算法专场】双指针(上)

目录 前言 基本原理 对撞指针 快慢指针 移动零 算法思路 算法步骤 代码实现 算法分析 复写零 算法思路 算法步骤 代码实现 快乐数 算法思路 算法步骤 代码实现 盛最多水的容器 ​编辑算法思路 代码实现 前言 双指针是一种在数组或链表等线性数据结构中高效…

GGUF模型转换入门

一、定义 1 定义 2 案例 二、实现 定义 GGUF是一种大模型文件格式&#xff0c;由开发者Georgi Gerganov提出。 这是一种针对大规模机器学习模型设计的二进制格式文件规范。它的主要优势在于能够将原始的大模型预训练结果经过特定优化后转换成这种格式&#xff0c;从而可以更…

jpg压缩的快速方法,分享4个!

在数字化时代&#xff0c;图片已成为我们生活和工作中不可或缺的一部分。然而&#xff0c;高质量的图片往往伴随着较大的文件大小&#xff0c;这在一定程度上影响了网页的加载速度和用户体验。为了解决这一问题&#xff0c;我们为大家精心挑选了4款jpg压缩软件&#xff0c;让你…

3种电脑截屏的快捷方式,告别繁琐操作,你值得拥有

无论是记录重要信息、分享有趣瞬间&#xff0c;还是制作教程和报告&#xff0c;截屏都是不可或缺的工具。当你想要迅速捕捉屏幕上的精彩瞬间&#xff0c;却发现不知如何截屏&#xff0c;是不是感到有些头疼&#xff1f;今天&#xff0c;就让小编揭晓3种电脑截屏的快捷方式&…

赏金猎人src挖掘入门

文章目录 1. 什么是漏洞2. OWASP Top 103. 利用的漏洞来源4. SRC安全应急响应中心5. Burpsuite简介6. 浏览器代理插件6.1 firefox浏览器代理插件6.2 edge浏览器代理插件3.chrome浏览器代理插件&#xff08;需要科学上网&#xff09; 1. 什么是漏洞 漏洞是指一个系统存在的弱点或…

springboot社区维修平台

设计技术&#xff1a; springboot、mysql、maven、前端vue 主要功能&#xff1a; 住户管理、社区公告管理、维修工管理、维修订单管理、接单信息管理、订单信息管理、在线沟通管理、举报信息管理、留言板管理、系统管理等功能模块。 管理员功能模块 管理员通过后台登录页面…

【知识学习】阐述Unity3D中Stencil的概念及使用方法示例

在Unity3D中&#xff0c;Stencil&#xff08;模板&#xff09;是一种高级的图形渲染技术&#xff0c;它允许开发者对渲染过程进行精细控制。Stencil Buffer是附加在颜色缓冲区和深度缓冲区之外的另一个缓冲区&#xff0c;它可以用来存储每个像素是否应该被渲染的信息。 Stenci…

记录samba账号操作日志,增删改查等(安全审计)

说明&#xff1a;windows用户映射samba文件共享服务&#xff0c;记录samba账号的操作日志 只要三步&#xff01; 安装必要软件包 audit配置samba共享配置Syslog 具体步骤 1. 安装必要的软件包 audit 是linux系统的高级审计框架 主要功能&#xff1a;系统调用监控、文件和目…

安科瑞智能物联网远传电表的优势

物联网远传智能电表是一种新型的电表&#xff0c;它通过物联网技术实现了电能的远程监测和管理。下面是物联网远传智能电表的优缺点&#xff1a;王盼盼&#xff1b;18721098782/Acrel 优点&#xff1a; 1. 实现了电能的远程监测和管理&#xff0c;可以随时随地了解电能的使用…

【EtherCAT】TwinCAT3通过PLC修改SDO数据

目录 1、打开twincat3, 左边PLC右键->添加新项&#xff0c;建立PLC工程 2、->References右键添加库 3、找到Tc2_EtherCAT库&#xff0c;点确定。 4、PLC程序ST语言就可以调用下面的功能块函数 5、PLC编程界面右键->输入助手 1、打开twincat3, 左边PLC右键->添…

7月开始,考研数学0️⃣基础线代30天满分规划

线代零基础&#xff1f; 那千万不要去跟李永乐老师的线代课程&#xff0c;因为李永乐老师的线代课程比较进阶&#xff0c;适合有一定基础的同学去听&#xff0c;下面这两位才是零基础线代的神&#xff01; 一个是喻老&#xff0c;另外一个是汤家凤&#xff01; 这两个老师的…