C++ 二叉树(建立、销毁、前中后序遍历和层次遍历,寻找双亲结点等)

news2024/11/23 21:20:58

(1)结构体和类定义

struct BTreeNode {
	T data;
	BTreeNode* left, * right;
	BTreeNode() :data(0), left(nullptr), right(nullptr) {}
	BTreeNode(T val, BTreeNode<T>* leftChild = nullptr, BTreeNode<T>* rightChild = nullptr)
		:data(val), left(leftChild), right(rightChild) {}

};

template<class T>
class BTree {
public:
	BTree() :root(nullptr) {}										      // 构造函数
	BTree(string str);                                                    // 重载

	void createTree(BTreeNode<T>*& bt, string str);                       // 创建二次树
	~BTree();														      // 析构函数
	bool IsEmpty();													      // 判二叉树空否?
	int Size(BTreeNode<T>* cur);                                          // 计算结点个数
	int getSize();                                                        // 获取结点个数
	BTreeNode<T>* getData(T& item, BTreeNode<T>* cur);	                  // 取得结点数据
	bool Find(T& item);		                                              // 判断item是否在树中
	int Height(BTreeNode<T>* bt);                                         // 求树高度
	int getHeight();                                                      // 获取树高度
	BTreeNode<T>* getRoot();	                                          // 取根

	void preOrderTraversal(BTreeNode<T>* cur, vector<int>& vec);          // 前序遍历
	void inOrderTraversal(BTreeNode<T>* cur, vector<int>& vec);		      // 中序遍历
	void postOrderTraversal(BTreeNode<T>* cur, vector<int>& vec);         // 后序遍历
	void levelOrderTraversal(BTreeNode<T>* cur, vector<int>& vec);        // 层序遍历

	vector<T> preOrder();						                          // 调用前序遍历,返回vector
	vector<T> inOrder();											      // 调用中序遍历,返回vector
	vector<T> postOrder();											      // 调用后序遍历,返回vector
	vector<T> levelOrder();                                               // 调用层序遍历,返回vector

	void CopyTree(BTreeNode<T>* root, BTreeNode<T>*& copyRoot);           // 二叉树复制
	void Copy(BTreeNode<T>*& copyRoot);                                   // 调用二叉树复制
	void destroyCopyTree(BTreeNode<T>*& copyRoot);                        // 销毁复制二叉树


	BTreeNode<T>* FindParent(BTreeNode<T>* root, BTreeNode<T>* node);     // 寻找双亲
	BTreeNode<T>* LeftChild(BTreeNode<T>* node) {                         //求结点 node 的左孩子
		return (node != nullptr) ? node->left : nullptr;
	}
	BTreeNode<T>* RightChild(BTreeNode<T>* node) {                        //求结点 node 的右孩子
		return (node != nullptr) ? node->right : nullptr;
	}

protected:
	BTreeNode<T>* root;
	void destroyTree(BTreeNode<T>* node);                                // 销毁二叉树
};

(2)创建二叉树

template<class T>
BTree<T>::BTree(string str) {
	createTree(root, str);
	cout << "报告:创建一颗二叉树,完成!!!" << endl;
}

template<class T>
void BTree<T>::createTree(BTreeNode<T>*& bt, string str) {
	static int i = 0;
	char ch = ' ';
	ch = str[i++];

	if (ch == '#') bt = nullptr;
	else {
		bt = new BTreeNode<T>(ch);
		createTree(bt->left, str);
		createTree(bt->right, str);
	}
};

(3)前中后序遍历和层序遍历

// 前序遍历
template<class T>
void BTree<T>::preOrderTraversal(BTreeNode<T>* cur, vector<int>& vec) {
	if (cur == nullptr)
		return;
	vec.push_back(cur->data);           // 中
	preOrderTraversal(cur->left, vec);  // 左
	preOrderTraversal(cur->right, vec); // 右
}

// 调用前序遍历,返回vector
template<class T>
vector<T> BTree<T>::preOrder() {
	cout << "获取前序遍历数组...." << endl;
	cout << ">>>>";
	vector<T> resVec;
	preOrderTraversal(root, resVec);
	return resVec;
}

// 中序遍历
template<class T>
void BTree<T>::inOrderTraversal(BTreeNode<T>* cur, vector<int>& vec) {
	if (cur == nullptr)
		return;
	inOrderTraversal(cur->left, vec);  // 左
	vec.push_back(cur->data);          // 中
	inOrderTraversal(cur->right, vec); // 右
}

// 调用中序遍历,返回vector
template<class T>
vector<T> BTree<T>::inOrder() {
	cout << "获取中序遍历数组...." << endl;
	cout << ">>>>";
	vector<T> resVec;
	inOrderTraversal(root, resVec);
	return resVec;
}

// 后序遍历
template<class T>
void BTree<T>::postOrderTraversal(BTreeNode<T>* cur, vector<int>& vec) {
	if (cur == nullptr)
		return;
	postOrderTraversal(cur->left, vec);  // 左
	postOrderTraversal(cur->right, vec); // 右
	vec.push_back(cur->data);            // 中
}

// 调用后序遍历,返回vector
template<class T>
vector<T> BTree<T>::postOrder() {
	cout << "获取后序遍历数组...." << endl;
	cout << ">>>>";
	vector<T> resVec;
	postOrderTraversal(root, resVec);
	return resVec;
}

// 层序遍历
template<class T>
void BTree<T>::levelOrderTraversal(BTreeNode<T>* cur, vector<int>& vec) {
	if (cur == nullptr) return;
	queue<BTreeNode<T>*> Queue;
	BTreeNode<T>* p;
	Queue.push(cur); // 根结点入队列
	while (!Queue.empty()) {
		p = Queue.front();
		//cout << p->data << " ";//输出出队结点的数据
		vec.push_back(p->data);
		Queue.pop();
		if (p->left != nullptr) {
			Queue.push(p->left);
		}
		if (p->right != nullptr) {
			Queue.push(p->right);
		}
	}
}

// 调用层序遍历,返回vector
template<class T>
vector<T> BTree<T>::levelOrder() {
	cout << "获取层序遍历数组...." << endl;
	cout << ">>>>";
	vector<T> resVec;
	levelOrderTraversal(root, resVec);
	return resVec;
}

(4)复制二叉树

template<class T>
void BTree<T>::CopyTree(BTreeNode<T>* root, BTreeNode<T>*& copyRoot) {
	if (!root) {
		copyRoot = nullptr;
	}
	else {
		copyRoot = new BTreeNode<T>;
		copyRoot->data = root->data;           //复制根节点
		CopyTree(root->left, copyRoot->left);  //递归复制左子树
		CopyTree(root->right, copyRoot->right);//递归复制左子树
	}
}

template<class T>
void BTree<T>::Copy(BTreeNode<T>*& copyRoot) {
	CopyTree(root, copyRoot);
}

(5)销毁二叉树

template<class T>
void BTree<T>::destroyCopyTree(BTreeNode<T>*& copyRoot) {
	destroyTree(copyRoot);
	cout << "报告,复制二叉树已销毁完毕!!!" << endl;
}

// 销毁二叉树 
template<class T>
void BTree<T>::destroyTree(BTreeNode<T>* bt) {
	// 后序遍历删除根为subTree的子树;
	if (bt != nullptr) {
		destroyTree(bt->left);    //删除左子树
		destroyTree(bt->right);   //删除右子树
		delete bt; 			      //删除根结点
	}
}

(6)析构函数

// 析构函数
template<class T>
BTree<T>::~BTree<T>() {
	//cout << "调用析构函数" << endl;
	destroyTree(root);
	cout << "报告,这棵树已经销毁完毕!!!" << endl;
}

(7)求树的高度

// 求树高度
template<class T>
int BTree<T>::Height(BTreeNode<T>* bt) {
	if (bt == nullptr) return 0;
	else {
		int leftH = Height(bt->left);
		int rightH = Height(bt->right);
		return (leftH > rightH) ? leftH + 1 : rightH + 1;
	}
}

// 获取树高度
template<class T>
int BTree<T>::getHeight() {
	return Height(root);
}

(8)获取结点,判断其是否在二叉树中

// 取得结点数据
template<class T>
BTreeNode<T>* BTree<T>::getData(T& item, BTreeNode<T>* cur) {
	if (cur == nullptr) return nullptr;
	if (cur->data == item) return cur;
	return getData(item, cur->left) != nullptr ? getData(item, cur->left) : getData(item, cur->right);
}

// 判断item是否在树中
template<class T>
bool BTree<T>::Find(T& item) {
	if (this->getData(item, root) == nullptr) return false;
	else return true;

(9)计算结点个数和获取结点个数

// 计算结点个数
template<class T>
int BTree<T>::Size(BTreeNode<T>* cur) {
	if (cur == nullptr)
		return 0;
	else
		return 1 + Size(cur->left) + Size(cur->right);
}

// 获取结点个数
template<class T>
int BTree<T>::getSize() {
	return Size(root);
}

(10)二叉树判空

// 判二叉树空否?
template<class T>
bool BTree<T>::IsEmpty() {
	return (root == nullptr) ? true : false;
}

(11)获取根结点

// 获取根 
template<class T>
BTreeNode<T>* BTree<T>::getRoot() {
	if (!root) return nullptr;
	else {
		return this->root;
	}
}

源代码:

btree.h

#pragma once
#include <iostream>
#include <vector>
#include <queue>
using namespace std;

template<class T>
struct BTreeNode {
	T data;
	BTreeNode* left, * right;
	BTreeNode() :data(0), left(nullptr), right(nullptr) {}
	BTreeNode(T val, BTreeNode<T>* leftChild = nullptr, BTreeNode<T>* rightChild = nullptr)
		:data(val), left(leftChild), right(rightChild) {}

};

template<class T>
class BTree {
public:
	BTree() :root(nullptr) {}										      // 构造函数
	BTree(string str);                                                    // 重载

	void createTree(BTreeNode<T>*& bt, string str);                       // 创建二次树
	~BTree();														      // 析构函数
	bool IsEmpty();													      // 判二叉树空否?
	int Size(BTreeNode<T>* cur);                                          // 计算结点个数
	int getSize();                                                        // 获取结点个数
	BTreeNode<T>* getData(T& item, BTreeNode<T>* cur);	                  // 取得结点数据
	bool Find(T& item);		                                              // 判断item是否在树中
	int Height(BTreeNode<T>* bt);                                         // 求树高度
	int getHeight();                                                      // 获取树高度
	BTreeNode<T>* getRoot();	                                          // 取根

	void preOrderTraversal(BTreeNode<T>* cur, vector<int>& vec);          // 前序遍历
	void inOrderTraversal(BTreeNode<T>* cur, vector<int>& vec);		      // 中序遍历
	void postOrderTraversal(BTreeNode<T>* cur, vector<int>& vec);         // 后序遍历
	void levelOrderTraversal(BTreeNode<T>* cur, vector<int>& vec);        // 层序遍历

	vector<T> preOrder();						                          // 调用前序遍历,返回vector
	vector<T> inOrder();											      // 调用中序遍历,返回vector
	vector<T> postOrder();											      // 调用后序遍历,返回vector
	vector<T> levelOrder();                                               // 调用层序遍历,返回vector

	void CopyTree(BTreeNode<T>* root, BTreeNode<T>*& copyRoot);           // 二叉树复制
	void Copy(BTreeNode<T>*& copyRoot);                                   // 调用二叉树复制
	void destroyCopyTree(BTreeNode<T>*& copyRoot);                        // 销毁复制二叉树


	BTreeNode<T>* FindParent(BTreeNode<T>* root, BTreeNode<T>* node);     // 寻找双亲
	BTreeNode<T>* LeftChild(BTreeNode<T>* node) {                         //求结点 node 的左孩子
		return (node != nullptr) ? node->left : nullptr;
	}
	BTreeNode<T>* RightChild(BTreeNode<T>* node) {                        //求结点 node 的右孩子
		return (node != nullptr) ? node->right : nullptr;
	}

protected:
	BTreeNode<T>* root;
	void destroyTree(BTreeNode<T>* node);                                // 销毁二叉树
};

btree.cpp

// 每次写递归,都按照这三要素来写,可以保证大家写出正确的递归算法!
// 1.确定递归函数的参数的返回值
// 2.确定终止条件
// 3.确定单层递归的逻辑

#include "btree.h"

template<class T>
BTree<T>::BTree(string str) {
	createTree(root, str);
	cout << "报告:创建一颗二叉树,完成!!!" << endl;
}

template<class T>
void BTree<T>::createTree(BTreeNode<T>*& bt, string str) {
	static int i = 0;
	char ch = ' ';
	ch = str[i++];

	if (ch == '#') bt = nullptr;
	else {
		bt = new BTreeNode<T>(ch);
		createTree(bt->left, str);
		createTree(bt->right, str);
	}
};

// 判二叉树空否?
template<class T>
bool BTree<T>::IsEmpty() {
	return (root == nullptr) ? true : false;
}

// 计算结点个数
template<class T>
int BTree<T>::Size(BTreeNode<T>* cur) {
	if (cur == nullptr)
		return 0;
	else
		return 1 + Size(cur->left) + Size(cur->right);
}

// 获取结点个数
template<class T>
int BTree<T>::getSize() {
	return Size(root);
}

// 取得结点数据
template<class T>
BTreeNode<T>* BTree<T>::getData(T& item, BTreeNode<T>* cur) {
	if (cur == nullptr) return nullptr;
	if (cur->data == item) return cur;
	return getData(item, cur->left) != nullptr ? getData(item, cur->left) : getData(item, cur->right);
}

// 判断item是否在树中
template<class T>
bool BTree<T>::Find(T& item) {
	if (this->getData(item, root) == nullptr) return false;
	else return true;
}

// 求树高度
template<class T>
int BTree<T>::Height(BTreeNode<T>* bt) {
	if (bt == nullptr) return 0;
	else {
		int leftH = Height(bt->left);
		int rightH = Height(bt->right);
		return (leftH > rightH) ? leftH + 1 : rightH + 1;
	}
}

// 获取树高度
template<class T>
int BTree<T>::getHeight() {
	return Height(root);
}

// 获取根 
template<class T>
BTreeNode<T>* BTree<T>::getRoot() {
	if (!root) return nullptr;
	else {
		return this->root;
	}
}

// 析构函数
template<class T>
BTree<T>::~BTree<T>() {
	//cout << "调用析构函数" << endl;
	destroyTree(root);
	cout << "报告,这棵树已经销毁完毕!!!" << endl;
}

// 销毁二叉树 
template<class T>
void BTree<T>::destroyTree(BTreeNode<T>* bt) {
	// 后序遍历删除根为subTree的子树;
	if (bt != nullptr) {
		destroyTree(bt->left);    //删除左子树
		destroyTree(bt->right);   //删除右子树
		delete bt; 			      //删除根结点
	}
}

// 前序遍历
template<class T>
void BTree<T>::preOrderTraversal(BTreeNode<T>* cur, vector<int>& vec) {
	if (cur == nullptr)
		return;
	vec.push_back(cur->data);           // 中
	preOrderTraversal(cur->left, vec);  // 左
	preOrderTraversal(cur->right, vec); // 右
}

// 调用前序遍历,返回vector
template<class T>
vector<T> BTree<T>::preOrder() {
	cout << "获取前序遍历数组...." << endl;
	cout << ">>>>";
	vector<T> resVec;
	preOrderTraversal(root, resVec);
	return resVec;
}

// 中序遍历
template<class T>
void BTree<T>::inOrderTraversal(BTreeNode<T>* cur, vector<int>& vec) {
	if (cur == nullptr)
		return;
	inOrderTraversal(cur->left, vec);  // 左
	vec.push_back(cur->data);          // 中
	inOrderTraversal(cur->right, vec); // 右
}

// 调用中序遍历,返回vector
template<class T>
vector<T> BTree<T>::inOrder() {
	cout << "获取中序遍历数组...." << endl;
	cout << ">>>>";
	vector<T> resVec;
	inOrderTraversal(root, resVec);
	return resVec;
}

// 后序遍历
template<class T>
void BTree<T>::postOrderTraversal(BTreeNode<T>* cur, vector<int>& vec) {
	if (cur == nullptr)
		return;
	postOrderTraversal(cur->left, vec);  // 左
	postOrderTraversal(cur->right, vec); // 右
	vec.push_back(cur->data);            // 中
}

// 调用后序遍历,返回vector
template<class T>
vector<T> BTree<T>::postOrder() {
	cout << "获取后序遍历数组...." << endl;
	cout << ">>>>";
	vector<T> resVec;
	postOrderTraversal(root, resVec);
	return resVec;
}

// 层序遍历
template<class T>
void BTree<T>::levelOrderTraversal(BTreeNode<T>* cur, vector<int>& vec) {
	if (cur == nullptr) return;
	queue<BTreeNode<T>*> Queue;
	BTreeNode<T>* p;
	Queue.push(cur); // 根结点入队列
	while (!Queue.empty()) {
		p = Queue.front();
		//cout << p->data << " ";//输出出队结点的数据
		vec.push_back(p->data);
		Queue.pop();
		if (p->left != nullptr) {
			Queue.push(p->left);
		}
		if (p->right != nullptr) {
			Queue.push(p->right);
		}
	}
}

// 调用层序遍历,返回vector
template<class T>
vector<T> BTree<T>::levelOrder() {
	cout << "获取层序遍历数组...." << endl;
	cout << ">>>>";
	vector<T> resVec;
	levelOrderTraversal(root, resVec);
	return resVec;
}

template<class T>
void BTree<T>::CopyTree(BTreeNode<T>* root, BTreeNode<T>*& copyRoot) {
	if (!root) {
		copyRoot = nullptr;
	}
	else {
		copyRoot = new BTreeNode<T>;
		copyRoot->data = root->data;           //复制根节点
		CopyTree(root->left, copyRoot->left);  //递归复制左子树
		CopyTree(root->right, copyRoot->right);//递归复制左子树
	}
}

template<class T>
void BTree<T>::Copy(BTreeNode<T>*& copyRoot) {
	CopyTree(root, copyRoot);
}

template<class T>
void BTree<T>::destroyCopyTree(BTreeNode<T>*& copyRoot) {
	destroyTree(copyRoot);
	cout << "报告,复制二叉树已销毁完毕!!!" << endl;
}

template<class T>
BTreeNode<T>* BTree<T>::FindParent(BTreeNode<T>* root, BTreeNode<T>* node) {

	if (root == nullptr) return nullptr;
	if (root->left == node || root->right == node)
		return root;	     //找到, 返回父结点地址
	BTreeNode <T>* p;
	if ((p = FindParent(root->left, node)) != nullptr)
		return p;	         //递归在左子树中搜索
	else return FindParent(root->right, node);
}

test.cpp

#include "btree.h"
#include "btree.cpp"
//#include <iostream>
//using namespace std;
int main() {
	cout << "-------------------------Start--------------------------" << endl;
	cout << "---------------------创建原始二叉树---------------------" << endl;
	string str = "ABD#G##E##CF###";
	BTree<int>* T = new BTree<int>(str);
	BTreeNode<int>* root = T->getRoot();
	cout << "这棵树有 " << T->getSize() << " 个结点" << endl;

	int zifu = 'G';
	if (T->Find(zifu)) {
		cout << "这棵树有 " << (char)zifu << " 结点" << endl;
	}
	else {
		cout << "这棵树无 " << (char)zifu << " 结点" << endl;
	}
	BTreeNode<int>* node = T->getData(zifu, root);
	if (node) {
		cout << (char)node->data << endl;
		BTreeNode<int>* nodeParent = T->FindParent(root, node);
		if (!nodeParent) {
			cout << "找不到父亲结点" << endl;
		}
		else {
			cout << "结点 " << (char)zifu << " 的父亲结点是: " << (char)nodeParent->data << " 结点" << endl;
			if (nodeParent->left) cout << "我的左孩子是: " << (char)nodeParent->left->data << endl;
			else cout << "我没有左孩子..." << endl;
			if (nodeParent->right) cout << "我的右孩子是: " << (char)nodeParent->right->data << endl;
			else cout << "我没有右孩子..." << endl;
		}
	}
	cout << "这棵树的高度为: " << T->getHeight() << endl;

	vector<int> vec = T->preOrder();
	for (auto i : vec) {
		cout << (char)i;
	}
	cout << endl;

	vec.clear();
	vec = T->inOrder();
	for (auto i : vec) {
		cout << (char)i;
	}
	cout << endl;

	vec.clear();
	vec = T->postOrder();
	for (auto i : vec) {
		cout << (char)i;
	}
	cout << endl;

	vec.clear();
	vec = T->levelOrder();
	for (auto i : vec) {
		cout << (char)i;
	}
	cout << endl;


	cout << "-----------------------复制二叉树-----------------------" << endl;
	// 复制二叉树
	//vector<int> vec;
	//BTreeNode<int>* root = T->getRoot();
	BTreeNode<int>* copyRoot = new BTreeNode<int>;
	//T->Copy(copyRoot);          // 方法一
	T->CopyTree(root, copyRoot);  // 方法二

	vec.clear();
	cout << "获取前序遍历数组...." << endl;
	cout << ">>>>";
	T->preOrderTraversal(copyRoot, vec);
	for (auto i : vec) {
		cout << (char)i;
	}
	cout << endl;

	vec.clear();
	cout << "获取中序遍历数组...." << endl;
	cout << ">>>>";
	T->inOrderTraversal(copyRoot, vec);
	for (auto i : vec) {
		cout << (char)i;
	}
	cout << endl;

	vec.clear();
	cout << "获取后序遍历数组...." << endl;
	cout << ">>>>";
	T->postOrderTraversal(copyRoot, vec);
	for (auto i : vec) {
		cout << (char)i;
	}
	cout << endl;

	vec.clear();
	cout << "获取层序遍历数组...." << endl;
	cout << ">>>>";
	T->levelOrderTraversal(copyRoot, vec);
	for (auto i : vec) {
		cout << (char)i;
	}
	cout << endl;
	cout << "---------------------销毁复制二叉树---------------------" << endl;
	T->destroyCopyTree(copyRoot);
	cout << "---------------------销毁原始二叉树---------------------" << endl;
	T->~BTree();
	cout << "--------------------------End---------------------------" << endl;
	return 0;
}

>>测试结果 

-------------------------Start--------------------------
---------------------创建原始二叉树---------------------
报告:创建一颗二叉树,完成!!!
这棵树有 7 个结点
这棵树有 G 结点
G
结点 G 的父亲结点是: D 结点
我没有左孩子...
我的右孩子是: G
这棵树的高度为: 4
获取前序遍历数组....
>>>>ABDGECF
获取中序遍历数组....
>>>>DGBEAFC
获取后序遍历数组....
>>>>GDEBFCA
获取层序遍历数组....
>>>>ABCDEFG
-----------------------复制二叉树-----------------------
获取前序遍历数组....
>>>>ABDGECF
获取中序遍历数组....
>>>>DGBEAFC
获取后序遍历数组....
>>>>GDEBFCA
获取层序遍历数组....
>>>>ABCDEFG
---------------------销毁复制二叉树---------------------
报告,复制二叉树已销毁完毕!!!
---------------------销毁原始二叉树---------------------
报告,这棵树已经销毁完毕!!!
--------------------------End---------------------------

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

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

相关文章

两个pdf合并成一个pdf怎么合并?这几个方法值得推荐

两个pdf合并成一个pdf怎么合并&#xff1f;pdf文件的合并是一个很常见的需求&#xff0c;特别是在处理工作文件或学习资料时。为了更好的帮助你了解如何将两个pdf文件合并成一个&#xff0c;下面就给大家详细介绍几种合并方法。 方法一&#xff1a;使用迅捷PDF转换器 这是一款…

【虫洞攻击检测】使用多层神经网络的移动自组织网络中的虫洞攻击检测研究(Matlab代码实现)

&#x1f4a5;&#x1f4a5;&#x1f49e;&#x1f49e;欢迎来到本博客❤️❤️&#x1f4a5;&#x1f4a5; &#x1f3c6;博主优势&#xff1a;&#x1f31e;&#x1f31e;&#x1f31e;博客内容尽量做到思维缜密&#xff0c;逻辑清晰&#xff0c;为了方便读者。 ⛳️座右铭&a…

一文教你学会Termux+SFTP+远程文件传输

文章目录 1. 安装openSSH2. 安装cpolar3. 远程SFTP连接配置4. 远程SFTP访问4. 配置固定远程连接地址 SFTP&#xff08;SSH File Transfer Protocol&#xff09;是一种基于SSH&#xff08;Secure Shell&#xff09;安全协议的文件传输协议。与FTP协议相比&#xff0c;SFTP使用了…

设计HTML5表格

在网页设计中&#xff0c;表格主要用于显示包含行、列结构的二维数据&#xff0c;如财务表格、调查数据、日历表、时刻表、节目表等。在大多数情况下&#xff0c;这类信息都由列标题或行标题及数据构成。本章将详细介绍表格在网页设计中的应用&#xff0c;包括设计符合标准化的…

页面跳转和两个页面之间的数据传递-鸿蒙ArkTS

页面跳转和两个页面之间的数据传递-ArkTS 页面跳转和两个页面之间的数据传递-ArkTS关于router的使用**跳转页面的实现方式。**页面接受跳转传递的参数页面返回及携带参数效果代码Index页面Second页面 参考资料 页面跳转和两个页面之间的数据传递-ArkTS 本篇文章主要是对两个页面…

怎么把CAD转成JPG图片?一个方法教你如何转换

CAD是计算机辅助设计的缩写&#xff0c;通常指的是AutoCAD软件所生成的DWG文件格式。DWG是一种二进制文件格式&#xff0c;用于保存2D和3D设计数据和元数据&#xff0c;支持多种操作系统和程序使用。该格式通常用于工程、建筑、制造和其他领域的设计和绘图。 CAD文件转换成JPG图…

企业安全架构体系的现状和解决方案

一、企业安全现状 从2016年底开始随着网络安全事件的爆发和国家层面对网络安全的重视程度&#xff0c;让网络安全已经上升到国家战略层面&#xff0c;同时网络空间已经成为领土、领海、领空和太空之外的第五空间&#xff0c; 是国家主权建设的新疆域。 随着中国对外开放的进一…

echarts tooltip提示框加单位

效果&#xff1a; 1.比较简单的方法 series: [{name: "重大风险",type: "bar",data: data2,color: ExtremeRiskColor,tooltip: {valueFormatter: function (value) {return value 个;}},},{name: "较大风险",type: "bar",data: dat…

GPT垂直领域相关模型 现有的开源领域大模型

对于ToC端来说&#xff0c;广大群众的口味已经被ChatGPT给养叼了&#xff0c;市场基本上被ChatGPT吃的干干净净。虽然国内大厂在紧追不舍&#xff0c;但目前绝大多数都还在实行内测机制&#xff0c;大概率是不会广泛开放的&#xff08;毕竟&#xff0c;各大厂还是主盯ToB、ToG市…

实例038 设置窗体在屏幕中的位置

实例说明 在窗体中可以设置窗体居中显示&#xff0c;本例通过设置窗体的Left属性和Top属性可以准确设置窗体的位置。运行本例&#xff0c;效果如图1.38所示。 技术要点 设置窗体在屏幕中的位置&#xff0c;可以通过设置窗体的属性来实现。窗体的Left属性表示窗体距屏幕左侧的…

问题:【IntelliJ IDEA】解决idea自动声明变量加finall修饰符问题

问题:【IntelliJ IDEA】解决idea自动声明变量加finall修饰符问题 场景复现 1 new String() 2 快捷方式生成变量 final修饰的 final String s new String();步骤一&#xff1a;确保settings配置信息 settings-----》Editor------》Code Style--------》java下的这两个选项不…

通过TightVNC远程访问MacOS

目录 一、下载 TightVNC 下载链接&#xff1a;https://www.tightvnc.com/ 下载后按步骤进行安装&#xff0c;安装完成后安装目录如下&#xff1a; 运行 tvnviewer.exe&#xff0c;输入远程 IP&#xff0c;点击【connect】&#xff1a; 输入密码&#xff0c;点击【OK】后即可远…

Android布局【TableLayout】

文章目录 说明常见属性子控件设置属性 项目结构主要代码 说明 TableLayout也称为表格布局 常见属性 android:collapseColumns&#xff1a;设置需要被隐藏的列的序列号&#xff0c;从0开始android:stretchColumns&#xff1a;设置允许被拉伸的列的列序号&#xff0c;从0开始&…

数据结构算法--2 冒泡排序,选择排序,插入排序

基础排序算法 冒泡排序 思想就是将相邻元素两两比较&#xff0c;当一个元素大于右侧相邻元素时&#xff0c;交换他们的位置&#xff0c;小于右侧元素时&#xff0c;位置不变&#xff0c;最终序列中的最大元素&#xff0c;像气泡一样&#xff0c;到了最右侧。 这时冒泡排序第一…

vulnhub靶场之ADROIT: 1.0.1

准备&#xff1a; 攻击机&#xff1a;虚拟机kali、本机win10。 靶机&#xff1a;Adroit: 1.0.1&#xff0c;下载地址&#xff1a;https://download.vulnhub.com/adroit/Adroit-v1.0.1.ova&#xff0c;下载后直接vbox打开即可。 知识点&#xff1a;shell反弹&#xff08;jar&…

接口自动化必备技能——jmeter提取token方式以及设置成全局变量(跨线程组传token值)方式

前言 今天Darren洋教大家如何使用jmeter中的插件来进行token值的提取与调用&#xff0c;今天Darren洋介绍两种jmeter提取token值的方式&#xff0c;一种是在当前线程组中直接提取token值&#xff0c;一种是跨线程组的方式进行token值的提取并调用给不同线程组里的HTTP接口使用。…

LeetCode算法递归类—平衡二叉树

目录 110. 平衡二叉树 题解&#xff1a; 运行结果&#xff1a; 优化版1&#xff1a; 运行结果&#xff1a; 给定一个二叉树&#xff0c;判断它是否是高度平衡的二叉树。 本题中&#xff0c;一棵高度平衡二叉树定义为&#xff1a; 一个二叉树每个节点 的左右两个子树的高度…

基于Bsdiff差分算法的汽车OTA升级技术研究(学习)

摘要 针对汽车OTA整包升级时&#xff0c;用户下载时间长&#xff0c;升级时间长&#xff0c;设备服务器端压力大等问题&#xff0c;本文提出了一种基于Bsdiff差分算法的汽车OTA升级技术。该算法能够对比新旧版本的差异&#xff0c;进行差分文件下载&#xff0c;减少软件包的下…

bat批处理启动jar包

echo off title “gwjy_sc(86)” java -jar -Xms512m -Xmx1024m -XX:MaxNewSize512m -XX:MaxPermSize512m gwjy_sc.jar --spring.config.localapplication.yml exit

Spring Bean的作用域和生命周期

文章目录 1. Bean的作用域2. Spring的生命周期3. Bean的生命周期4. 相关注解总结 1. Bean的作用域 Bean 的作用域指的是 Bean 在 Spring 容器中的行为&#xff08;Bean 实例创建及生命周期&#xff09;&#xff0c;它的行为是由 Spring 来管理的&#xff0c;可以根据具体情况选…