MySQL表结构导出(Excel)

       

目录

一、java实现MySQL表结构导出(Excel)

二、python实现MySQL表结构导出(Excel)


        又到了写毕设的时候了,计算机专业在写论文第四章系统设计的时候肯定会遇到和我一样的难题——要在论文中将数据库的表结构以表格形式展示出来,小编在度娘搜了很多文章,但是收获不大,很多没有达到我的预期(以表格形式展示出来)。

        最后,小编决定发挥一下idea的作用,自己写一个工具类,打印数据库中的表的表结构,最后将其保存到excel表中,这样更加方便移到论文中。

        废话不多说,咱们直接开始。

一、java实现MySQL表结构导出(Excel)

MysqlExporterToExcel.java类

package com.example.demo.utils;import javax.swing.*;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.sql.*;
import java.util.HashMap;
import java.util.Map;import org.apache.poi.ss.usermodel.*;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;public class MysqlExporterToExcel extends JFrame {private JTextField hostField;private JTextField userField;private JPasswordField passwordField;private JTextField databaseField;private JTextField outputFileField;public MysqlExporterToExcel() {setTitle("MySQL 表结构导出工具");setSize(600, 400);setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);setLocationRelativeTo(null);JPanel panel = new JPanel();panel.setLayout(new GridLayout(6, 2));JLabel hostLabel = new JLabel("主机:");hostField = new JTextField("localhost");JLabel userLabel = new JLabel("用户名:");userField = new JTextField("root");JLabel passwordLabel = new JLabel("密码:");passwordField = new JPasswordField("123456");JLabel databaseLabel = new JLabel("数据库:");databaseField = new JTextField("");// 设置默认输出路径和文件名String defaultPath = "C:/software/mysql/table_structure.xlsx";JLabel outputFileLabel = new JLabel("输出文件:");outputFileField = new JTextField(defaultPath);JButton exportButton = new JButton("导出");panel.add(hostLabel);panel.add(hostField);panel.add(userLabel);panel.add(userField);panel.add(passwordLabel);panel.add(passwordField);panel.add(databaseLabel);panel.add(databaseField);panel.add(outputFileLabel);panel.add(outputFileField);panel.add(new JLabel());panel.add(exportButton);add(panel);exportButton.addActionListener(new ActionListener() {@Overridepublic void actionPerformed(ActionEvent e) {String host = hostField.getText();String user = userField.getText();String password = new String(passwordField.getPassword());String database = databaseField.getText();String outputFile = outputFileField.getText();// 输入验证if (host.isEmpty() || user.isEmpty() || database.isEmpty() || outputFile.isEmpty()) {JOptionPane.showMessageDialog(MysqlExporterToExcel.this,"请确保主机、用户名、数据库和输出文件都已填写", "输入错误", JOptionPane.ERROR_MESSAGE);return;}// 检查并创建目录File file = new File(outputFile);File parentDir = file.getParentFile();if (!parentDir.exists()) {if (!parentDir.mkdirs()) {JOptionPane.showMessageDialog(MysqlExporterToExcel.this,"无法创建目录: " + parentDir.getAbsolutePath(), "目录创建失败", JOptionPane.ERROR_MESSAGE);return;}}exportTableStructure(host, user, password, database, outputFile);}});}private void exportTableStructure(String host, String user, String password, String database, String outputFile) {String url = "jdbc:mysql://" + host + ":3306/" + database;try (Connection connection = DriverManager.getConnection(url, user, password);Statement statement = connection.createStatement();Workbook workbook = new XSSFWorkbook()) {// 检查数据库连接是否成功if (connection.isValid(5)) {Sheet sheet = workbook.createSheet("表结构");ResultSet tables = statement.executeQuery("SHOW TABLES");int rowNum = 0;String[] headers = {"序号", "名称", "类型", "空", "长度", "主键", "说明", "其他备注"};while (tables.next()) {String tableName = tables.getString(1);// 写入表名相关信息Row tableNameRow = sheet.createRow(rowNum++);tableNameRow.createCell(0).setCellValue("表名:");tableNameRow.createCell(1).setCellValue(tableName);// 写入表头Row headerRow = sheet.createRow(rowNum++);for (int col = 0; col < headers.length; col++) {Cell cell = headerRow.createCell(col);cell.setCellValue(headers[col]);}// 获取主键信息ResultSet primaryKeys = connection.getMetaData().getPrimaryKeys(null, null, tableName);Map<String, Boolean> primaryKeyMap = new HashMap<>();while (primaryKeys.next()) {String primaryKeyColumn = primaryKeys.getString("COLUMN_NAME");primaryKeyMap.put(primaryKeyColumn, true);}primaryKeys.close();ResultSet columns = connection.getMetaData().getColumns(null, null, tableName, null);ResultSetMetaData metaData = columns.getMetaData();int extraColumnIndex = -1;for (int i = 1; i <= metaData.getColumnCount(); i++) {if ("EXTRA".equalsIgnoreCase(metaData.getColumnName(i))) {extraColumnIndex = i;break;}}int serialNumber = 1;while (columns.next()) {String columnName = columns.getString("COLUMN_NAME");String columnType = columns.getString("TYPE_NAME");int nullable = columns.getInt("NULLABLE");String isNullable = (nullable == ResultSetMetaData.columnNullable)? "是" : "否";int columnSize = columns.getInt("COLUMN_SIZE");String isPrimaryKey = primaryKeyMap.containsKey(columnName)? "是" : "否";// 简单的字段名翻译示例,可根据实际情况扩展String description = translateColumnName(columnName);String extra = "";if (extraColumnIndex != -1) {extra = columns.getString(extraColumnIndex);}if ("".equals(extra)) {extra = "<空>";}Row row = sheet.createRow(rowNum++);row.createCell(0).setCellValue(serialNumber++);row.createCell(1).setCellValue(columnName);row.createCell(2).setCellValue(columnType);row.createCell(3).setCellValue(isNullable);row.createCell(4).setCellValue(columnSize);row.createCell(5).setCellValue(isPrimaryKey);row.createCell(6).setCellValue(description);row.createCell(7).setCellValue(extra);}// 在每个表的信息后插入一个空行sheet.createRow(rowNum++);}tables.close();// 调整列宽for (int col = 0; col < headers.length; col++) {sheet.autoSizeColumn(col);}// 保存 Excel 文件try (FileOutputStream fileOut = new FileOutputStream(outputFile)) {workbook.write(fileOut);JOptionPane.showMessageDialog(this, "表结构已成功导出到 " + outputFile);}} else {JOptionPane.showMessageDialog(this, "无法连接到数据库", "连接错误", JOptionPane.ERROR_MESSAGE);}} catch (SQLException sqlEx) {if (sqlEx.getSQLState().startsWith("28")) {JOptionPane.showMessageDialog(this, "用户名或密码错误", "认证错误", JOptionPane.ERROR_MESSAGE);} else if (sqlEx.getSQLState().startsWith("08")) {JOptionPane.showMessageDialog(this, "无法连接到数据库,请检查主机和端口", "连接错误", JOptionPane.ERROR_MESSAGE);} else {JOptionPane.showMessageDialog(this, "导出失败: " + sqlEx.getMessage(), "错误", JOptionPane.ERROR_MESSAGE);}} catch (IOException ioEx) {JOptionPane.showMessageDialog(this, "文件写入失败: " + ioEx.getMessage(), "文件错误", JOptionPane.ERROR_MESSAGE);}}private String translateColumnName(String columnName) {// 简单的翻译映射,可根据实际情况扩展Map<String, String> translationMap = new HashMap<>();translationMap.put("id", "编号");translationMap.put("name", "名称");translationMap.put("age", "年龄");// 可以继续添加更多的翻译映射return translationMap.getOrDefault(columnName, "");}public static void main(String[] args) {SwingUtilities.invokeLater(new Runnable() {@Overridepublic void run() {MysqlExporterToExcel exporter = new MysqlExporterToExcel();exporter.setVisible(true);}});}
}

在java中还要引入依赖,这我就不细说了。

<!--导出表--><dependency><groupId>org.apache.poi</groupId><artifactId>poi-ooxml</artifactId><version>5.2.3</version></dependency>

这样就可以了。

我们看一下运行效果:

上面的都可以修改。

小提醒:最后就是数据库的问题

在java类中,我写的是

String url = "jdbc:mysql://" + host + ":3306/" + database;

因为安装数据库时默认端口为3306,可能你在安装时3306被占用,比如你在安装时输入的是3308,这里也要改为3308。

二、python实现MySQL表结构导出(Excel)

可能有的人要问了,小编小编,我不会java怎么办啊,考虑到一些同学没有学习java,我写了一个pyhton版。下面就是python的代码

import tkinter as tk
from tkinter import messagebox
import pymysql
from openpyxl import Workbook
import osclass MysqlTableStructureExporter:def __init__(self):self.root = tk.Tk()self.root.title("MySQL 表结构导出工具")# 定义输入框和标签tk.Label(self.root, text="主机:").grid(row=0, column=0)self.host_field = tk.Entry(self.root, width=30)  # 修改宽度为 30self.host_field.insert(0, "localhost")self.host_field.grid(row=0, column=1)tk.Label(self.root, text="用户名:").grid(row=1, column=0)self.user_field = tk.Entry(self.root, width=30)  # 修改宽度为 30self.user_field.insert(0, "root")self.user_field.grid(row=1, column=1)tk.Label(self.root, text="密码:").grid(row=2, column=0)self.password_field = tk.Entry(self.root, show="*", width=30)  # 修改宽度为 30self.password_field.insert(0, "123456")self.password_field.grid(row=2, column=1)tk.Label(self.root, text="数据库:").grid(row=3, column=0)self.database_field = tk.Entry(self.root, width=30)  # 修改宽度为 30self.database_field.grid(row=3, column=1)tk.Label(self.root, text="输出文件:").grid(row=4, column=0)default_path = "C:/software/mysql/table_structure.xlsx"self.output_file_field = tk.Entry(self.root, width=30)  # 修改宽度为 30self.output_file_field.insert(0, default_path)self.output_file_field.grid(row=4, column=1)# 导出按钮export_button = tk.Button(self.root, text="导出", command=self.export_table_structure)export_button.grid(row=5, column=0, columnspan=2)def run(self):self.root.mainloop()def export_table_structure(self):host = self.host_field.get()user = self.user_field.get()password = self.password_field.get()database = self.database_field.get()output_file = self.output_file_field.get()# 输入验证if not host or not user or not database or not output_file:messagebox.showerror("输入错误", "请确保主机、用户名、数据库和输出文件都已填写")return# 检查并创建目录output_dir = os.path.dirname(output_file)if not os.path.exists(output_dir):try:os.makedirs(output_dir)except OSError:messagebox.showerror("目录创建失败", f"无法创建目录: {output_dir}")returntry:# 连接数据库connection = pymysql.connect(host=host, user=user, password=password, database=database)cursor = connection.cursor()# 创建 Excel 工作簿和工作表workbook = Workbook()sheet = workbook.activesheet.title = "表结构"# 获取所有表名cursor.execute("SHOW TABLES")tables = cursor.fetchall()row_num = 0for table in tables:table_name = table[0]# 写入表名sheet.cell(row=row_num + 1, column=1, value="表名:")sheet.cell(row=row_num + 1, column=2, value=table_name)row_num += 1# 写入表头headers = ["序号", "名称", "类型", "空", "长度", "主键", "说明", "其他备注"]for col, header in enumerate(headers, start=1):sheet.cell(row=row_num + 1, column=col, value=header)row_num += 1# 获取主键信息cursor.execute(f"SHOW KEYS FROM {table_name} WHERE Key_name = 'PRIMARY'")primary_keys = [row[4] for row in cursor.fetchall()]# 获取表的列信息cursor.execute(f"SHOW FULL COLUMNS FROM {table_name}")columns = cursor.fetchall()serial_number = 1for column in columns:column_name = column[0]column_type = column[1]is_nullable = "是" if column[2] == "YES" else "否"column_size = column[1].split("(")[-1].rstrip(")") if "(" in column[1] else ""is_primary_key = "是" if column_name in primary_keys else "否"description = self.translate_column_name(column_name)extra = column[8] if column[8] else "<空>"sheet.cell(row=row_num + 1, column=1, value=serial_number)sheet.cell(row=row_num + 1, column=2, value=column_name)sheet.cell(row=row_num + 1, column=3, value=column_type)sheet.cell(row=row_num + 1, column=4, value=is_nullable)sheet.cell(row=row_num + 1, column=5, value=column_size)sheet.cell(row=row_num + 1, column=6, value=is_primary_key)sheet.cell(row=row_num + 1, column=7, value=description)sheet.cell(row=row_num + 1, column=8, value=extra)row_num += 1serial_number += 1# 插入空行row_num += 1# 调整列宽for column in sheet.columns:max_length = 0column_letter = column[0].column_letterfor cell in column:try:if len(str(cell.value)) > max_length:max_length = len(str(cell.value))except:passadjusted_width = (max_length + 2)sheet.column_dimensions[column_letter].width = adjusted_width# 保存 Excel 文件workbook.save(output_file)messagebox.showinfo("导出成功", f"表结构已成功导出到 {output_file}")except pymysql.Error as e:if e.args[0] in [1045]:  # 认证错误messagebox.showerror("认证错误", "用户名或密码错误")elif e.args[0] in [2003]:  # 连接错误messagebox.showerror("连接错误", "无法连接到数据库,请检查主机和端口")else:messagebox.showerror("错误", f"导出失败: {str(e)}")except Exception as e:messagebox.showerror("文件错误", f"文件写入失败: {str(e)}")finally:if 'connection' in locals():connection.close()def translate_column_name(self, column_name):# 简单的翻译映射,可根据实际情况扩展translation_map = {"id": "编号","name": "名称","age": "年龄"}return translation_map.get(column_name, "")if __name__ == "__main__":exporter = MysqlTableStructureExporter()exporter.run()

复制代码后直接导入包就行。

我们来看一下运行效果

效果还是不错的。如果要修改可以根据上面java的来改,方法类似。

最后看一下excel表吧

可以看到非常清楚,方便复制

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

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

相关文章

Android使用OpenGL和MediaCodec渲染视频

目录 一&#xff0c;借助MediaCodec封装解码工具类VideoCodec 二&#xff0c;使用OpenGl绘制视频封装SoulFilter 一&#xff0c;借助MediaCodec封装解码工具类VideoCodec /*** 解码工具类* 解码完成后的数据 通过 ISurface 回调出去*/ public class VideoCodec {private ISu…

day39——输入操作:多值输入

数组输入&#xff1a; int main() {//***** 1、多值输入&#xff08;C&#xff09;/*输入&#xff1a;3 --> 3个值5 4 9*/int n;cin >> n; //输入个数const int MAX_SIZE 0xFFFF;//限定最大个数int a[MAX_SIZE];for (int i 0; i < n; i) {//用 n 作控制输入…

第九课:LoRA模型的原理及应用

文章目录 Part.01 3种LoRA的使用方式Part.02 5种LoRA的应用方向Part.01 3种LoRA的使用方式 LoRA能够在家用级设备上训练,实现对Checkpoint在某些方面的微调使用Lora的三种方式:放置Lora模型到目录中,然后作为提示词的一部分输入。点击生成按钮下面的“画”,然后打开Additio…

Cortex-M3 NVIC可以控制异常向量表的哪些部分

Cortex-M3 的 NVIC(嵌套向量中断控制器)不直接控制整个异常向量表,但可以管理向量表中与中断相关的部分行为。以下是 NVIC 对异常向量表的具体控制范围和相关机制: 1. NVIC 直接控制的部分 NVIC 主要管理 外部中断(IRQ) 和部分 系统异常 的行为,但对向量表本身的存储位…

双向链表增删改查的模拟实现

本章目标 0.双向链表的基本结构 1.双向链表的初始化 2.头插尾插 3.头删尾删 4.查找与打印 5.在指定位置之前插入数据/在指定位置之后插入数据 6.在指定位置之前删除数据/在指定位置之后删除数据 7.销毁链表 0.双向链表的基本结构 本章所实现的双向链表是双向循环带头链表,是…

实战交易策略 篇十四:江南神鹰捕捉热点和熊市生存交易策略

文章目录 系列文章捕捉热点是股市最大的掘金术市场温度不低于50是热点产生的必要条件题材的大小和新颖程度决定热点的持续时间和涨幅炒作热点的3个阶段捕捉热点的方法与步骤操作实战案例熊市生存术“熊市最好的做法是离开股市”的说法是一句空话熊市盈利模式:不轻言底部,超跌…

Linux错误(6)X64向量指令访问地址未对齐引起SIGSEGV

Linux错误(6)X64向量指令访问地址未对齐引起SIGSEGV Author: Once Day Date: 2025年4月4日 一位热衷于Linux学习和开发的菜鸟&#xff0c;试图谱写一场冒险之旅&#xff0c;也许终点只是一场白日梦… 漫漫长路&#xff0c;有人对你微笑过嘛… 全系列文章可参考专栏: Linux实…

解码 __iter__ 和 itertools.islice - 迭代的艺术

文章目录 前言一、`_iter__`:自定义迭代的钥匙1.1 什么是 __iter__?1.2 基本用法1.3 高级用法:独立迭代器二、itertools.islice:迭代切片的利器2.1 什么是 itertools.islice?2.2 基本用法2.3 处理无限序列2.4 实际应用三、`__iter__` 与 `islice` 的结合六、为什么需要它们…

使用VSCode编写C#程序

目录 一、环境搭建&#xff1a;构建高效开发基础1. 安装VSCode2. 配置.NET SDK3. 安装核心扩展 二、项目开发全流程1. 创建项目2. 代码编辑技巧3. 调试配置4. 高级调试技巧5. 编译与运行 三、常见问题解决指南1. 项目加载失败2. IntelliSense失效3. 代码格式化4. 典型编译错误&…

日本汽车规模性经济计划失败,日产三大品牌的合并合作共赢,还是绝地求生?本田与日产合并确认失败,将成为世界第三大汽车集团愿景失败

本田与日产(含三菱汽车)的合并计划最终因核心矛盾无法调和而宣告失败,这一事件揭示了传统车企在行业变革期的深层困境。以下从合并动机、失败原因、本质判断及未来影响等方面综合分析: 一、合并的初衷:生存压力主导的被动策略 市场危机与财务困境 中国市场溃败:日系品牌在…

AutoCAD2026中文版下载安装教程

AutoCAD是一款由Autodesk公司开发的计算机辅助设计软件&#xff0c;被广泛应用于建筑设计、机械设计、电气设计、土木工程、装饰装潢等多个领域。AutoCAD2026中文版在原有的基础上进行了多项改进和优化&#xff0c;为用户提供了更为高效、便捷的绘图和设计体验。这里我给大家分…

Latex语法入门之数学公式

Latex是一种高质量的排版系统&#xff0c;尤其擅长于数学公式的排版。本文我将带大家深入了解Latex在数学公式排版中的应用。从基础的数学符号到复杂的公式布局&#xff0c;我们都会一一讲解&#xff0c;通过本文的学习&#xff0c;你将能够轻松编写出清晰、美观的数学公式&…

洛谷 P3214 [HNOI2011] 卡农

题目传送门 前言 再次败在 d p dp dp 手下&#xff0c;但是数据范围这么小应该是可以看出是 d p dp dp 的&#xff08;毕竟对于其他组合数的问题数据范围都是 1 0 9 10^9 109 起步&#xff09;。 思路 题意简化 现有 1 , 2 , 3 , . . . , n − 1 , n 1, 2, 3, ... , n -…

【年份数据类型及使用】

在数据分析中,年份的处理需要根据具体场景选择合适的数据类型,以确保后续分析的准确性和效率。以下是常见的年份数据类型及使用场景: 1. 数值类型(整数或浮点数) 适用场景: 仅需存储年份数值(如 2020, 2023),无需进行日期计算。需要将年份作为连续变量参与数学运算(如…

详解七大排序

目录 一.直接插入排序 &#xff08;1&#xff09;基本思想 &#xff08;2&#xff09;算法步骤 &#xff08;3&#xff09;代码实现 &#xff08;4&#xff09;算法特性 &#xff08;5&#xff09;算法优化 &#xff08;6&#xff09;示例演示 二.希尔排序 &#xff08…

YOLOv12 训练从这里开始:LabelImg 标注数据集

视频讲解&#xff1a; YOLOv12 训练从这里开始&#xff1a;LabelImg 标注数据集 labelimg https://github.com/tzutalin/labelImg sudo apt-get install pyqt5-dev-tools pip3 install lxml git clone https://github.com/tzutalin/labelImg.git cd labelImg 开始编译 make…

Day2:前端项目uniapp壁纸实战

先来做一个轮番图。 效果如下&#xff1a; common-style.css view,swiper,swiper-item{box-sizing: border-box; } index.vue <template><view class"homeLayout"><view class"banner"><swiper circular indicator-dots autoplay…

SAP-ABAP:ABAP `LEAVE LIST-PROCESSING` 深度解析

ABAP LEAVE LIST-PROCESSING 深度解析 核心机制 模式切换(Dialog → List) 中断屏幕流 强制终止当前Dialog程序的PBO/PAI处理,脱离屏幕序列控制(如事务码SE38执行的程序)。触发报表事件 激活类报表程序的事件链:INITIALIZATION → AT SELECTION-SCREEN → START-OF-SEL…

在PyTorch中使用GPU加速:从基础操作到模型部署

本文将通过具体代码示例&#xff0c;详细介绍如何在PyTorch中利用GPU进行张量计算和模型训练&#xff0c;包含设备查询、数据迁移以及模型部署等完整流程。 1. 查看GPU硬件信息 使用 nvidia-smi 命令检查GPU状态和进程信息&#xff1a; # 查看GPU信息 !nvidia-smi 输出示例&…

lib-zo,C语言另一个协程库,dns协程化, gethostbyname

lib-zo,C语言另一个协程库,dns协程化, gethostbyname 另一个 C 协程库 https://blog.csdn.net/eli960/article/details/146802313 本协程库 支持 DNS查询 协程化. 禁用所有 UDP 协程化 zvar_coroutine_disable_udp 1;禁用 53 端口的UDP 协程化 zvar_coroutine_disable_ud…