数组 - 八皇后 - 困难
*************
C++
topic: 面试题 08.12. 八皇后 - 力扣(LeetCode)
*************
Good morning, gays, Fridary angin and try the hard to celebrate.
Inspect the topic:

This topic I can understand it in a second. And I do rethink a movie, which talks anout chess

This title imposes the same rectructions on queens as the rules for queens in chess. In chess, queens may move either stright and diagonally. And may by this code was applied in some chees games.

Back to the topic, try to find the topics I've done which is similar to t his topic. It seems like no one like this.
Use matrix, I learned matrix from a teacher, Master Tang:

Greedy algorithm, I did yesterday, may work. Every step goes to the best way, and might have the happy ending in the end.
First, put the queen in matrix[1][1], then put the second row, maxtrix[2][1] is forbidden cuz it is in the first column. Matrix[2][2] is forbidden cuz it in the diagonal. Put it in matrix[2][3]. Actally, make sure that matrix[i][i] put nothing.

From the first row, put the queen in the first column.
To the second row, put the queen in the first column, check if it conflicts with previous queens. If not, add a row. If so, change a column.
Take an example, N = 13, The position-array has 13 elements, each ranges from 0 to 12.
For each increatment, generate a new array of positions. Check if the condition is satisfied for each array of positions. If satisfied, save it.
When the last queen find her place, the war end.
This is a really new algorithm called Backtracking Algorithm.A backtracking algorithm is an algorithm that tries different things until it finds the right answer. It avoids doing unnecessary work. Backtracking algorithms are used to solve many kinds of problems. The usage of backtracking algorithm follows:
void backtrack(路径参数, 选择列表参数) {// 检查是否满足结束条件if (满足结束条件) {// 处理解决方案return;}// 遍历选择列表for (auto i : 选择列表) {// 添加当前选项到路径路径.push_back(i);// 进行递归backtrack(路径, 更新的选择列表);// 回溯,移除当前选项路径.pop_back();}
}
Try to write the code:
need to find a right way to describe the chess board. matrix N × N doesnot work, the reason of it is that memory is everything for the computer, N × N use tooooooooooooo much storage. Never think about it.
Every queen has different row, so it can be used in one-line matrix, for instace:

it can be described as 4 multiply 4
- 1 0 0 0
- 0 0 1 0
- 0 1 0 0
- 0 0 0 1
also, a smarter way to describe is as follow:
array X = [1, 3, 2, 4], which means
- the 1st queen laies at row 1 column 1,
- the 2nd queen laies at row 2 column 3,
- the 3rd queen laies at row 3 column 2,
- the 4th queen laies at row 4 column 4,
but how to tell the computer that the queens cannot stay in the diagonal?

the same color's position is illegal. It can EZ tell that two queens on the same diagonal if and only if their row and column differences are equal.
|row1 - row4| == |column4 - column1|
There's no need to double-check each row and column; only the diagonals. To check more efficiently, record which columns and diagonals have been used when placing the queens.
record this in three sets:
- Columns where queens have already been placed.
- Primary diagonal: row-column values on the same primary diagonal.
- Sub-diagonal: row + column values where identical values are on the same sub-diagonal.
so make up the code to describe the 3 sets in backtrack structure:
void backtrack_bit(int n, int row, unsigned long long cols_mask,unsigned long long diag1_mask, unsigned long long diag2_mask,vector<int>& queens, vector<vector<string>>& result)
{// 检查是否满足结束条件if (满足结束条件) {// 处理解决方案return;}// 遍历选择列表for (auto i : 选择列表) {// 添加当前选项到路径路径.push_back(i);// 进行递归backtrack(路径, 更新的选择列表);// 回溯,移除当前选项路径.pop_back();}
}
move next, what is 满足结束条件? it is the row == n, the last queen finds her palace.
void backtrack_bit(int n, int row, unsigned long long cols_mask,unsigned long long diag1_mask, unsigned long long diag2_mask,vector<int>& queens, vector<vector<string>>& result)
{// 检查是否满足结束条件if (row == n) {// 处理解决方案return;}// 遍历选择列表for (auto i : 选择列表) {// 添加当前选项到路径路径.push_back(i);// 进行递归backtrack(路径, 更新的选择列表);// 回溯,移除当前选项路径.pop_back();}
}
and what is 处理解决方案? That is return the result. But pay vital attention to the result like this:
![]()
make sure that the code return a string:
void backtrack_bit(int n, int row, unsigned long long cols_mask,unsigned long long diag1_mask, unsigned long long diag2_mask,vector<int>& queens, vector<vector<string>>& result)
{// 检查是否满足结束条件if (row == n) {// 生成棋盘的字符串表示vector<string> board;for (int i = 0; i < n; i++) {string row_str(n, '.'); // 初始化一行,全部为'.'row_str[queens[i]] = 'Q'; // 在皇后的位置放置'Q'board.push_back(row_str); // 将这一行添加到棋盘表示中}result.push_back(board); // 将整个棋盘添加到结果中return;}// 遍历选择列表for (auto i : 选择列表) {// 添加当前选项到路径路径.push_back(i);// 进行递归backtrack(路径, 更新的选择列表);// 回溯,移除当前选项路径.pop_back();}
}
the next step is 遍历选择列表. This is the most diffcult step, including how to lay the queens. Make sure that every column has been visited.
void backtrack_bit(int n, int row, unsigned long long cols_mask,unsigned long long diag1_mask, unsigned long long diag2_mask,vector<int>& queens, vector<vector<string>>& result)
{// 检查是否满足结束条件if (row == n) {// 生成棋盘的字符串表示vector<string> board;for (int i = 0; i < n; i++) {string row_str(n, '.'); // 初始化一行,全部为'.'row_str[queens[i]] = 'Q'; // 在皇后的位置放置'Q'board.push_back(row_str); // 将这一行添加到棋盘表示中}result.push_back(board); // 将整个棋盘添加到结果中return;}// 遍历选择列表for (int col = 0; col < n; col++) {// 添加当前选项到路径路径.push_back(i);// 进行递归backtrack(路径, 更新的选择列表);// 回溯,移除当前选项路径.pop_back();}
}
If there's already a queen in the column, main diagonal, or sub-diagonal where you're placing the queen, skip that spot.
void backtrack_bit(int n, int row, unsigned long long cols_mask,unsigned long long diag1_mask, unsigned long long diag2_mask,vector<int>& queens, vector<vector<string>>& result)
{// 检查是否满足结束条件if (row == n) {// 生成棋盘的字符串表示vector<string> board;for (int i = 0; i < n; i++) {string row_str(n, '.'); // 初始化一行,全部为'.'row_str[queens[i]] = 'Q'; // 在皇后的位置放置'Q'board.push_back(row_str); // 将这一行添加到棋盘表示中}result.push_back(board); // 将整个棋盘添加到结果中return;}// 遍历选择列表for (int col = 0; col < n; col++) {if ((cols_mask & (1ULL << col)) ||(diag1_mask & (1ULL << d1)) ||(diag2_mask & (1ULL << d2))) {continue; // 如果不安全,跳过这一列}// 添加当前选项到路径路径.push_back(i);// 进行递归backtrack(路径, 更新的选择列表);// 回溯,移除当前选项路径.pop_back();}
}
in this special code :
if ((cols_mask & (1ULL << col)) ||(diag1_mask & (1ULL << d1)) ||(diag2_mask & (1ULL << d2))) {continue; // 如果不安全,跳过这一列}
1ULL meas 1 unsigned long long, << means move 1 step to the left.
diag_mask is an integer, for example:
if col == 2, in binary system is 10; 1ULL << 2 is 4, in binary system is 100
see, in binary system, int 1 moves one step left.
then put the queen
void backtrack_bit(int n, int row, unsigned long long cols_mask,unsigned long long diag1_mask, unsigned long long diag2_mask,vector<int>& queens, vector<vector<string>>& result)
{// 检查是否满足结束条件if (row == n) {// 生成棋盘的字符串表示vector<string> board;for (int i = 0; i < n; i++) {string row_str(n, '.'); // 初始化一行,全部为'.'row_str[queens[i]] = 'Q'; // 在皇后的位置放置'Q'board.push_back(row_str); // 将这一行添加到棋盘表示中}result.push_back(board); // 将整个棋盘添加到结果中return;}// 遍历选择列表for (int col = 0; col < n; col++) {if ((cols_mask & (1ULL << col)) ||(diag1_mask & (1ULL << d1)) ||(diag2_mask & (1ULL << d2))) {continue; // 如果不安全,跳过这一列}// 在当前位置放置皇后queens.push_back(col);// 进行递归backtrack(路径, 更新的选择列表);// 回溯,移除当前选项路径.pop_back();}
}
and move to the next row:
void backtrack_bit(int n, int row, unsigned long long cols_mask,unsigned long long diag1_mask, unsigned long long diag2_mask,vector<int>& queens, vector<vector<string>>& result)
{// 检查是否满足结束条件if (row == n) {// 生成棋盘的字符串表示vector<string> board;for (int i = 0; i < n; i++) {string row_str(n, '.'); // 初始化一行,全部为'.'row_str[queens[i]] = 'Q'; // 在皇后的位置放置'Q'board.push_back(row_str); // 将这一行添加到棋盘表示中}result.push_back(board); // 将整个棋盘添加到结果中return;}// 遍历选择列表for (int col = 0; col < n; col++) {if ((cols_mask & (1ULL << col)) ||(diag1_mask & (1ULL << d1)) ||(diag2_mask & (1ULL << d2))) {continue; // 如果不安全,跳过这一列}// 在当前位置放置皇后queens.push_back(col);// 递归到下一行backtrack_bit(n, row + 1, cols_mask | (1ULL << col),diag1_mask | (1ULL << d1), diag2_mask | (1ULL << d2),queens, result);// 回溯,移除当前选项路径.pop_back();}
}
and next
void backtrack_bit(int n, int row, unsigned long long cols_mask,unsigned long long diag1_mask, unsigned long long diag2_mask,vector<int>& queens, vector<vector<string>>& result)
{// 检查是否满足结束条件if (row == n) {// 生成棋盘的字符串表示vector<string> board;for (int i = 0; i < n; i++) {string row_str(n, '.'); // 初始化一行,全部为'.'row_str[queens[i]] = 'Q'; // 在皇后的位置放置'Q'board.push_back(row_str); // 将这一行添加到棋盘表示中}result.push_back(board); // 将整个棋盘添加到结果中return;}// 遍历选择列表for (int col = 0; col < n; col++) {if ((cols_mask & (1ULL << col)) ||(diag1_mask & (1ULL << d1)) ||(diag2_mask & (1ULL << d2))) {continue; // 如果不安全,跳过这一列}// 在当前位置放置皇后queens.push_back(col);// 递归到下一行backtrack_bit(n, row + 1, cols_mask | (1ULL << col),diag1_mask | (1ULL << d1), diag2_mask | (1ULL << d2),queens, result);// 回溯,移除当前皇后queens.pop_back();}
}
dont forget to initialize at the very beginning:
class Solution {
public:// 主函数,接收一个整数n,表示棋盘的大小vector<vector<string>> solveNQueens(int n) {vector<vector<string>> result; // 用于存储所有可能的解vector<int> queens; // 用于存储当前放置皇后的列位置// 从第0行开始回溯backtrack_bit(n, 0, 0, 0, 0, queens, result);return result; // 返回所有可能的解}private:// 回溯函数,参数包括棋盘大小n,当前行row,以及三个掩码void backtrack_bit(int n, int row, unsigned long long cols_mask,unsigned long long diag1_mask, unsigned long long diag2_mask,vector<int>& queens, vector<vector<string>>& result) {// 如果到达最后一行,说明找到了一个解if (row == n) {// 生成棋盘的字符串表示vector<string> board;for (int i = 0; i < n; i++) {string row_str(n, '.'); // 初始化一行,全部为'.'row_str[queens[i]] = 'Q'; // 在皇后的位置放置'Q'board.push_back(row_str); // 将这一行添加到棋盘表示中}result.push_back(board); // 将整个棋盘添加到结果中return;}// 尝试在当前行的每一列放置皇后for (int col = 0; col < n; col++) {int d1 = row - col + (n - 1); // 对角线1的索引int d2 = row + col; // 对角线2的索引// 检查当前位置是否安全if ((cols_mask & (1ULL << col)) ||(diag1_mask & (1ULL << d1)) ||(diag2_mask & (1ULL << d2))) {continue; // 如果不安全,跳过这一列}// 在当前位置放置皇后queens.push_back(col);// 递归到下一行backtrack_bit(n, row + 1, cols_mask | (1ULL << col),diag1_mask | (1ULL << d1), diag2_mask | (1ULL << d2),queens, result);// 回溯,移除当前皇后queens.pop_back();}}
};
and of course it works:

unsigned longlong can be replaced as unsigned long, to save the storge.
class Solution {
public:// 主函数,接收一个整数n,表示棋盘的大小vector<vector<string>> solveNQueens(int n) {vector<vector<string>> result; // 用于存储所有可能的解vector<int> queens; // 用于存储当前放置皇后的列位置// 从第0行开始回溯backtrack_bit(n, 0, 0, 0, 0, queens, result);return result; // 返回所有可能的解}private:// 回溯函数,参数包括棋盘大小n,当前行row,以及三个掩码void backtrack_bit(int n, int row, unsigned long cols_mask,unsigned long diag1_mask, unsigned long diag2_mask,vector<int>& queens, vector<vector<string>>& result) {// 如果到达最后一行,说明找到了一个解if (row == n) {// 生成棋盘的字符串表示vector<string> board;for (int i = 0; i < n; i++) {string row_str(n, '.'); // 初始化一行,全部为'.'row_str[queens[i]] = 'Q'; // 在皇后的位置放置'Q'board.push_back(row_str); // 将这一行添加到棋盘表示中}result.push_back(board); // 将整个棋盘添加到结果中return;}// 尝试在当前行的每一列放置皇后for (int col = 0; col < n; col++) {int d1 = row - col + (n - 1); // 对角线1的索引int d2 = row + col; // 对角线2的索引// 检查当前位置是否安全if ((cols_mask & (1UL << col)) ||(diag1_mask & (1UL << d1)) ||(diag2_mask & (1UL << d2))) {continue; // 如果不安全,跳过这一列}// 在当前位置放置皇后queens.push_back(col);// 递归到下一行backtrack_bit(n, row + 1, cols_mask | (1UL << col),diag1_mask | (1UL << d1), diag2_mask | (1UL << d2),queens, result);// 回溯,移除当前皇后queens.pop_back();}}
};
and here is the magic:

consume memory ranges from 11.96 to 12.15.
reverse upgrading, sad.

anyway
wish me have a good weekend.
相关文章:
数组 - 八皇后 - 困难
************* C topic: 面试题 08.12. 八皇后 - 力扣(LeetCode) ************* Good morning, gays, Fridary angin and try the hard to celebrate. Inspect the topic: This topic I can understand it in a second. And I do rethink a movie, …...
【分布式】Redis分布式缓存
一、什么是Redis分布式缓存 Redis分布式缓存是指使用Redis作为缓存系统来存储和管理数据的分布式方案。在分布式系统中,多台服务器共同对外提供服务,为了提高系统的性能和可扩展性,通常会引入缓存来减轻数据库的压力。Redis作为一种高性能的…...
Ubuntu——extrepo添加部分外部软件源
extrepo 是一个用于 Ubuntu 和其他基于 Debian 的系统的工具,它的主要作用是简化和管理外部软件源(repositories)的添加和更新。通过使用 extrepo,用户可以方便地添加、删除和管理第三方软件源,而不需要手动编辑源列表…...
评估大语言模型(LLM)在分子预测任务能够理解分子几何形状性能
摘要 论文地址:https://arxiv.org/pdf/2403.05075 近年来,机器学习模型在各个领域越来越受欢迎。学术界和工业界都投入了大量精力来提高机器学习的效率,以期实现人工通用智能(AGI)。其中,大规模语言模型&a…...
如何查看电脑刷新率
Windows 系统 通过显示设置查看: 右键点击桌面空白处,选择 “显示设置”。在打开的窗口中,找到 “高级显示设置”。点击 “显示适配器属性”。在弹出的窗口中,选择 “监视器” 选项卡,即可看到当前的屏幕刷新率。使用 …...
mysql集群MHA方式部署
1. 基本信息 部署机器角色部署路径192.168.242.71MySQL-Mater MHA-NodeMySQL: /alidata1/mysql-8.0.28192.168.242.72MySQL-Slave MHA-NodeMHA-Node: /alidata1/admin/tools/mha4mysql-node-0.58192.168.242.73MySQL-Slave MHA-Node192.168.242.74MHA-ManagerMHA-Manager: …...
第十七章 使用 MariaDB 数据库管理系统
1. 数据库管理系统 数据库是指按照某些特定结构来存储数据资料的数据仓库。在当今这个大数据技术迅速崛起的年代,互联网上每天都会生成海量的数据信息,数据库技术也从最初只能存储简单的表格数据的单一集中存储模式,发展到了现如今存储海量…...
rabbitmq 安装延时队列插件rabbitmq_delayer_message_exchange(linux centOS 7)
1.插件版本 插件地址:Community Plugins | RabbitMQ rabbitmq插件需要对应的版本,根据插件地址找到插件 rabbitmq_delayer_message_exchange 点击Releases 因为我rabbitmq客户端显示的版本是: 所以我选择插件版本是: 下载 .ez文…...
Unity性能优化---动态网格组合(一)
网格组合是将 Unity 中的多个对象组合为一个对象的技术。因此,在多物体的场景中,使用网格组合,会有效的减少小网格的数量,最终将得到一个包含许多小网格的大网格游戏对象,这将提高游戏或模拟器的性能。在Unity 的 “St…...
Appium:安装uiautomator2失败
目录 1、通过nmp安装uiautomator2:失败 2、通过 Appium 的平台直接安装驱动程序 3、通过pip 来安装 uiautomator2 1、通过nmp安装uiautomator2:失败 我先是通过npm安装的uiautomator2,也显示已经安装成功了: npm install -g …...
电子信息工程自动化 单片机彩灯控制
摘要 随着社会经济和科学技术的不断进步,人们在保持发展的同时,环境带给人类的影响已经不足以让我们忽视,所以城市的美化问题慢慢的进入了人们的眼帘,PLC的产生给带电子产品带来了巨大变革,彩灯的使用在城市的美化中变…...
word poi-tl 表格功能增强,实现表格功能垂直合并
目录 问题解决问题poi-tl介绍 功能实现引入依赖模版代码效果图 附加(插件实现)MergeColumnData 对象MergeGroupData 类ServerMergeTableData 数据信息ServerMergeTablePolicy 合并插件 问题 由于在开发功能需求中,word文档需要垂直合并表格&…...
LSTM-CNN-BP-RF-SVM五模型咖喱融合策略混合预测模型
目录 效果一览基本介绍程序设计参考资料 效果一览 基本介绍 LSTM-CNN-BP-RF-SVM五模型咖喱融合策略混合预测模型 Matlab代码注释清晰。 程序设计 完整程序和数据获取方式:私信博主回复LSTM-CNN-BP-RF-SVM五模型咖喱融合策略混合预测模型(Matlab&#…...
《鸿蒙开发-答案之书》 怎么设置Json字段的别名
《鸿蒙开发-答案之书》 怎么设置Json字段的别名 Android设置别名用的是SerializedName(“msg”),那鸿蒙用的是啥,有点懵不知道。 鸿蒙得引入第三方库:ohpm install class-transformer 然后用Expose({ name: ‘first-name’ }) 示例代码&…...
ftp服务器搭建-安装、配置及验证
ftp服务器搭建-安装、配置及验证 #安装 sudo apt-get install vsftpd #配置文件 cat > /etc/vsftpd.conf << "EOF" listenNO listen_ipv6YES anonymous_enableNO local_enableYES write_enableYES dirmessage_enableYES use_localtimeYES xferlog_enable…...
鸿蒙应用获取wifi连接的ip地址(官方文档获取的格式转换成192.168.1.xxx格式)
目录 一.背景 二.官网流程 wifiManager.getLinkedInfo9+ 三.转换成192.168.xxx.xxx格式 一.背景 本次来学习如何获取到鸿蒙设备连接wifi后的ip地址,由于官网文档中获取的ip地址和我们平时看到的192:168:xxx:xxx有所不同,需要进行下转换,所以记录下,如下的流程是在OpenH…...
c++数据结构算法复习基础--11--高级排序算法-快速排序-归并排序-堆排序
高阶排序 1、快速排序 冒泡排序的升级算法 每次选择一个基准数,把小于基准数的放到基准数的左边,把大于基准数的放到基准数的右边,采用 “ 分治算法 ”处理剩余元素,直到整个序列变为有序序列。 最好和平均的复杂度:…...
人工智能学习路线详细规划
一、引言 在当今科技飞速发展的时代,人工智能已成为引领未来的关键技术之一。无论是为了追求职业发展的新机遇,还是出于对这一前沿领域的浓厚兴趣,深入学习人工智能都是一个极具价值的选择。本文将为大家精心规划一条人工智能学习路线&#…...
深度学习之视觉处理
CNN 视觉处理三大任务:分类、目标检测、图像分割上游:提取特征,CNN下游:分类、目标、分割等,具体的任务 概述 卷积神经网络是深度学习在计算机视觉领域的突破性成果。在计算机视觉领域, 往往我们输入的图像都很大&am…...
遇到问题:hive中的数据库和sparksql 操作的数据库不是同一个。
遇到的问题: 1、hive中的数据库和sparksql 操作的数据库不同步。 观察上面的数据库看是否同步 !!! 2、查询服务器中MySQL中hive的数据库,发现创建的位置没有在hdfs上,而是在本地。 这个错误产生的原因是&…...
【网络】每天掌握一个Linux命令 - iftop
在Linux系统中,iftop是网络管理的得力助手,能实时监控网络流量、连接情况等,帮助排查网络异常。接下来从多方面详细介绍它。 目录 【网络】每天掌握一个Linux命令 - iftop工具概述安装方式核心功能基础用法进阶操作实战案例面试题场景生产场景…...
【OSG学习笔记】Day 18: 碰撞检测与物理交互
物理引擎(Physics Engine) 物理引擎 是一种通过计算机模拟物理规律(如力学、碰撞、重力、流体动力学等)的软件工具或库。 它的核心目标是在虚拟环境中逼真地模拟物体的运动和交互,广泛应用于 游戏开发、动画制作、虚…...
DockerHub与私有镜像仓库在容器化中的应用与管理
哈喽,大家好,我是左手python! Docker Hub的应用与管理 Docker Hub的基本概念与使用方法 Docker Hub是Docker官方提供的一个公共镜像仓库,用户可以在其中找到各种操作系统、软件和应用的镜像。开发者可以通过Docker Hub轻松获取所…...
Python:操作 Excel 折叠
💖亲爱的技术爱好者们,热烈欢迎来到 Kant2048 的博客!我是 Thomas Kant,很开心能在CSDN上与你们相遇~💖 本博客的精华专栏: 【自动化测试】 【测试经验】 【人工智能】 【Python】 Python 操作 Excel 系列 读取单元格数据按行写入设置行高和列宽自动调整行高和列宽水平…...
Java-41 深入浅出 Spring - 声明式事务的支持 事务配置 XML模式 XML+注解模式
点一下关注吧!!!非常感谢!!持续更新!!! 🚀 AI篇持续更新中!(长期更新) 目前2025年06月05日更新到: AI炼丹日志-28 - Aud…...
第一篇:Agent2Agent (A2A) 协议——协作式人工智能的黎明
AI 领域的快速发展正在催生一个新时代,智能代理(agents)不再是孤立的个体,而是能够像一个数字团队一样协作。然而,当前 AI 生态系统的碎片化阻碍了这一愿景的实现,导致了“AI 巴别塔问题”——不同代理之间…...
#Uniapp篇:chrome调试unapp适配
chrome调试设备----使用Android模拟机开发调试移动端页面 Chrome://inspect/#devices MuMu模拟器Edge浏览器:Android原生APP嵌入的H5页面元素定位 chrome://inspect/#devices uniapp单位适配 根路径下 postcss.config.js 需要装这些插件 “postcss”: “^8.5.…...
华为OD机试-最短木板长度-二分法(A卷,100分)
此题是一个最大化最小值的典型例题, 因为搜索范围是有界的,上界最大木板长度补充的全部木料长度,下界最小木板长度; 即left0,right10^6; 我们可以设置一个候选值x(mid),将木板的长度全部都补充到x,如果成功…...
AI语音助手的Python实现
引言 语音助手(如小爱同学、Siri)通过语音识别、自然语言处理(NLP)和语音合成技术,为用户提供直观、高效的交互体验。随着人工智能的普及,Python开发者可以利用开源库和AI模型,快速构建自定义语音助手。本文由浅入深,详细介绍如何使用Python开发AI语音助手,涵盖基础功…...
MySQL的pymysql操作
本章是MySQL的最后一章,MySQL到此完结,下一站Hadoop!!! 这章很简单,完整代码在最后,详细讲解之前python课程里面也有,感兴趣的可以往前找一下 一、查询操作 我们需要打开pycharm …...
