多智能体(机器人)任务分配问题求解AssignmentProblem

news2024/11/26 10:15:33

问题提出:
N个智能体,现在有个任务,就是让N个智能体要到N个目标位置,目标位置不能重复,目标位置与机器人一一对应,要使得期间所有所走的距离之和最短,求解最优任务分配。

在这里插入图片描述

问题抽象:
有N个师父, N个徒弟,每个徒弟只能选者一个师父学习, 每个师父只能带一个徒弟; 每个师父有自己的技能,每个徒弟有自己学习的天分, 当徒弟 j 在师父 i 门下学习, 产生效益为 Aij, 问如何安排使得总效益最大?

求解过程:

定义数据格式:
m i : 第 i 个 师 父 , i = 1 , 2 , 3 , ⋯ , n m_i: 第 i 个师父, i=1,2,3,⋯,n mi:i,i=1,2,3,,n
t j : 第 j 个 徒 弟 , j = 1 , 2 , 3 , ⋯ n , t_j: 第 j 个徒弟,j=1,2,3,⋯n, tj:j,j=1,2,3,n,
x i j : 第 j 个 徒 弟 是 否 在 第 i 个 师 父 门 下 学 习 : 1 , 是 ; 2 不 是 . x_{ij}: 第j 个徒弟是否在第i 个师父门下学习: 1, 是; 2 不是. xij:ji:1,;2.
a i j : 第 j 个 徒 弟 在 第 i 个 师 父 门 下 学 习 产 生 的 效 益 . a_{ij}:第j 个徒弟在第i 个师父门下学习产生的效益. aij:ji.

数学模型:

y = m a x ∑ i = 1 n a i j . x i j ( 式 0 ) y=max \sum_{i=1}^n a_{ij}.x_{ij} { ( 式0)} y=maxi=1naij.xij(0)
∑ i = 1 n x i j = 1 , ∀ j = 1 , 2 , 3 , ⋯ , n ( 式 1 ) \sum_{i=1}^n x_{ij} =1 , \forall j=1,2,3,⋯,n { ( 式1)} i=1nxij=1,j=1,2,3,,n(1)
∑ j = 1 n x i j = 1 , ∀ i = 1 , 2 , 3 , ⋯ , n ( 式 2 ) \sum_{j=1}^n x_{ij} =1 , \forall i=1,2,3,⋯,n { ( 式2)} j=1nxij=1,i=1,2,3,,n(2)

x i j ∈ { 0 , 1 } ∀ i = 1 , 2 , 3 , ⋯ , n ; j = 1 , 2 , 3 , ⋯ , n ( 式 3 ) x_{ij} \in {\lbrace0,1}\rbrace \forall i=1,2,3,⋯,n;j=1,2,3,⋯,n (式3) xij{0,1}i=1,2,3,,n;j=1,2,3,,n(3)

  • 式0 为目标函数, 即最大化总效益;
  • 式1 表示一个师父只能带一个徒弟;
  • 式2 表示一个徒弟只能跟一个师父学习;
  • 式3表示师父-徒弟分配是原子操作,要么分配要么不分配。

在这个抽象的例子中,我们把
师父    ⟺    \iff 智能体(机器人)
徒弟    ⟺    \iff 要去的目标位置位置
效益    ⟺    \iff 智能体(机器人)当前位置与目标位置二者之间距离

当然这个例子中是求最小,师父徒弟的例子是求最大,道理是一样的。

匈牙利算法

解决分配问题最常用的是匈牙利算法。

按照知乎上某位博主的支付报酬、矩阵求解思路:

若从指派问题的系数矩阵的某行(列)各元素中分别减去或者加上常数k,其最优任务分解问题不变。

这里是引用

通过寻找“0”元素巧妙得出0报酬的指派思路:
给出的代码如下:

#include <stdio.h>
typedef struct matrix
{
	int cost[101][101];
	int zeroelem[101][101];
 	int costforout[101][101];
 	int matrixsize;
}MATRIX;
MATRIX hungary;
int result[5041][2];								//用来储存解的结果,第一列表示工人第二列表示工件 
void zeroout(MATRIX &hungary);						//减去行列的最小值得到零元素 
void circlezero(MATRIX &hungary);					//圈出单行列零元素 
void twozero(MATRIX &hungary);						//圈出行列存在两个以上的零元素 
void judge(MATRIX &hungary,int result[2000][2]);	//判断是否符合匈牙利算法条件 
void refresh(MATRIX &hungary);						//不符合条件,对矩阵进行变形 
void output(int result[2000][2],MATRIX hungary);	//结果输出 
MATRIX input();										//初始输入 
int main()
{
	result[0][0]=0;
	hungary=input();
	zeroout(hungary);
	circlezero(hungary); 
	output(result,hungary);
}
MATRIX input()
{
	int i,j; 
	matrix hungary;
	printf("指派问题的匈牙利解法\n");
	printf("请输入cost矩阵的阶数:\n");
	scanf("%d",&hungary.matrixsize);
	printf("请输入代表工人和工件的%d阶矩阵:\n",hungary.matrixsize);
	for(i=1;i<=hungary.matrixsize;i++)
  		for(j=1;j<=hungary.matrixsize;j++)
  		{   
 			scanf("%d",&hungary.cost[i][j]);
 			hungary.costforout[i][j]=hungary.cost[i][j];
  		}

 	return hungary;
}
void zeroout(MATRIX &hungary)
{
	int i,j; 
	int tem;	//表示同行的最大元素或同列的最大元素 
	for(i=1;i<=hungary.matrixsize;i++)             //减去同行最大元素
 	{ 
  	 	tem=hungary.cost[i][1];
  	 	for(j=2;j<=hungary.matrixsize;j++)
    	if(hungary.cost[i][j]<tem)
    		tem=hungary.cost[i][j];
  		for(j=1;j<=hungary.matrixsize;j++)
   		hungary.cost[i][j]=hungary.cost[i][j]-tem;
 	}
 	for(j=1;j<=hungary.matrixsize;j++)            //减去同列最大元素
 	{
  		tem=hungary.cost[1][j];
  		for(i=2;i<=hungary.matrixsize;i++)
     	if(hungary.cost[i][j]<tem)
    		tem=hungary.cost[i][j];
  		for(i=1;i<=hungary.matrixsize;i++)
  			hungary.cost[i][j]=hungary.cost[i][j]-tem;
 	}
}
void circlezero(MATRIX &hungary)
{
	int i,j,p;  
	int flag; 
 	for(i=0;i<=hungary.matrixsize;i++)                         //在矩阵外面构建半圈矩阵标记0的个数;
  		hungary.cost[i][0]=0; 
 	for(j=1;j<=hungary.matrixsize;j++)
  		hungary.cost[0][j]=0;
 	for(i=1;i<=hungary.matrixsize;i++)
  		for(j=1;j<=hungary.matrixsize;j++)
   		if(hungary.cost[i][j]==0)
   		{
    		hungary.cost[i][0]++;
    		hungary.cost[0][j]++;
    		hungary.cost[0][0]++;
   		} 
 	for(i=0;i<=hungary.matrixsize;i++)               //新建一个矩阵
  		for(j=0;j<=hungary.matrixsize;j++)           
   			hungary.zeroelem[i][j]=0;   
 	flag=hungary.cost[0][0]+1;                         //flag = 0的总个数+1
	while(hungary.cost[0][0]<flag)                   
	{
  		flag=hungary.cost[0][0];                                       //行列单0的情况,
  		for(i=1;i<=hungary.matrixsize;i++)                             //第一遍先行后列
	 	{
   			if(hungary.cost[i][0]==1) 
			{
				for(j=1;j<=hungary.matrixsize;j++)                        
     			if(hungary.cost[i][j]==0&&hungary.zeroelem[i][j]==0)
      				break;
    			hungary.zeroelem[i][j]=1;
    			hungary.cost[i][0]--;
   		 		hungary.cost[0][j]--;
    			hungary.cost[0][0]--;
    			if(hungary.cost[0][j]>0)
     			for(p=1;p<=hungary.matrixsize;p++)
      			if(hungary.cost[p][j]==0&&hungary.zeroelem[p][j]==0)
      			{
       				hungary.zeroelem[p][j]=2;
       				hungary.cost[p][0]--;
       				hungary.cost[0][j]--;
       				hungary.cost[0][0]--;
      			}      
			}                           
	
  		}
		for(j=1;j<=hungary.matrixsize;j++)                            //   第二遍先列后行
 		{
   			if(hungary.cost[0][j]==1)
			{
		    	for(i=1;i<=hungary.matrixsize;i++)
     			if(hungary.cost[i][j]==0&&hungary.zeroelem[i][j]==0)
      				break;
    			hungary.zeroelem[i][j]=1;
    			hungary.cost[i][0]--;
    			hungary.cost[0][j]--;
    			hungary.cost[0][0]--;
    			if(hungary.cost[i][0]>0)
     			for(p=1;p<=hungary.matrixsize;p++)
      			if(hungary.cost[i][p]==0&&hungary.zeroelem[i][p]==0)
      			{
       				hungary.zeroelem[i][p]=2;
       				hungary.cost[i][0]--;
       				hungary.cost[0][p]--;
       				hungary.cost[0][0]--;
      			}
			}
  		}
	}
	if(hungary.cost[0][0]>0)
		twozero(hungary);
	else
		judge(hungary,result);
}
void judge(MATRIX &hungary,int result[5041][2])
{
	int i,j;
 	int num=0;	//线的条数 
 	int start;	//每组解的储存开始位置 
 	for(i=1;i<=hungary.matrixsize;i++)
  		for(j=1;j<=hungary.matrixsize;j++)
   		if(hungary.zeroelem[i][j]==1)
    		num++;						//划线的条数 
		if(num==hungary.matrixsize)
		{
  			start=result[0][0]*hungary.matrixsize+1;
   			for(i=1;i<=hungary.matrixsize;i++)
    			for(j=1;j<=hungary.matrixsize;j++)
     				if(hungary.zeroelem[i][j]==1)
     				{
      					result[start][0]=i;
      					result[start++][1]=j;
     				}
   					result[0][0]++;
  		}
 		else
  			refresh(hungary);
}
void twozero(MATRIX &hungary)
{
	int i,j;
	int p,q;
	int m,n;
	int flag;
    MATRIX backup;
	for(i=1;i<=hungary.matrixsize;i++)
		if(hungary.cost[i][0]>0)
			break;
	if(i<=hungary.matrixsize)
	{
		for(j=1;j<=hungary.matrixsize;j++)
		{
			backup=hungary;//备份以寻找多解 
			if(hungary.cost[i][j]==0&&hungary.zeroelem[i][j]==0)
			{
    			hungary.zeroelem[i][j]=1;
    			hungary.cost[i][0]--;
    			hungary.cost[0][j]--;
    			hungary.cost[0][0]--;
    			for(q=1;q<=hungary.matrixsize;q++)
     				if(hungary.cost[i][q]==0&&hungary.zeroelem[i][q]==0)
     				{
      					hungary.zeroelem[i][q]=2;
      					hungary.cost[i][0]--;
      					hungary.cost[0][q]--;
      					hungary.cost[0][0]--;
     				}
    			for(p=1;p<=hungary.matrixsize;p++)
     				if(hungary.cost[p][j]==0&&hungary.zeroelem[p][j]==0)
     				{
      					hungary.zeroelem[p][j]=2;
      					hungary.cost[p][0]--;
      					hungary.cost[0][j]--;
      					hungary.cost[0][0]--;
     				}
    			flag=hungary.cost[0][0]+1;
    			while(hungary.cost[0][0]<flag)
    			{
     				flag=hungary.cost[0][0];
     				for(p=i+1;p<=hungary.matrixsize;p++)
     				{
     			 		if(hungary.cost[p][0]==1)
						{
       						for(q=1;q<=hungary.matrixsize;q++)
        						if(hungary.cost[p][q]==0&&hungary.zeroelem[p][q]==0)
         							break;
       							hungary.zeroelem[p][q]=1;
       							hungary.cost[p][0]--;
       							hungary.cost[0][q]--;
       							hungary.cost[0][0]--;
       						for(m=1;m<=hungary.matrixsize;m++)
        						if(hungary.cost[m][q]==0&&hungary.zeroelem[m][q]==0)
        						{
        			 				hungary.zeroelem[m][q]=2;
         							hungary.cost[m][0]--;
         							hungary.cost[0][q]--;
         							hungary.cost[0][0]--;
        						}
      					}
     				}
     				for(q=1;q<=hungary.matrixsize;q++)
     				{
      					if(hungary.cost[0][q]==1)
						{
       						for(p=1;p<=hungary.matrixsize;p++)
        						if(hungary.cost[p][q]==0&&hungary.zeroelem[p][q]==0)
         							break;
       							hungary.zeroelem[p][q]=1;
       							hungary.cost[p][q]--;
       							hungary.cost[0][q]--;
       							hungary.cost[0][0]--;
       						for(n=1;n<=hungary.matrixsize;n++)
        						if(hungary.cost[p][n]==0&&hungary.zeroelem[p][n]==0)
								{
         							hungary.zeroelem[p][n]=2;
         							hungary.cost[p][0]--;
         							hungary.cost[0][n]--;
         							hungary.cost[0][0]--;
        						}
      					}
     				}
    			}
    			if(hungary.cost[0][0]>0)                   //确保hungary.cost[][]中的0元素都在zeroelem[][]中被完全标记出来。
     				twozero(hungary);
    			else 
     				judge(hungary,result);
   			}           
   			hungary=backup;
  		}
 	}
}
void refresh(MATRIX &hungary)
{
	int i,j,min=0;
	int flag1=0,flag2=0;
	for(i=1;i<=hungary.matrixsize;i++)
	{
		for(j=1;j<=hungary.matrixsize;j++)
		if(hungary.zeroelem[i][j]==1)
		{
			hungary.zeroelem[i][0]=1;         //有独立零元素
    		break;
   		}
	}
	while(flag1==0)
	{
		flag1=1;
		for(i=1;i<=hungary.matrixsize;i++)
			if(hungary.zeroelem[i][0]==0)
			{
				hungary.zeroelem[i][0]=2;
				for(j=1;j<=hungary.matrixsize;j++)
					if(hungary.zeroelem[i][j]==2)
					{
						hungary.zeroelem[0][j]=1;
					}
   			}
		for(j=1;j<=hungary.matrixsize;j++)
		{
			if(hungary.zeroelem[0][j]==1)
			{
				hungary.zeroelem[0][j]=2;
				for(i=1;i<=hungary.matrixsize;i++)
    				if(hungary.zeroelem[i][j]==1)
					{
						hungary.zeroelem[i][0]=0;
      					flag1=0;
     				}
   			}
  		}
 	}                    //对打勾的行和列标记成2 
	for(i=1;i<=hungary.matrixsize;i++)
	{
		if(hungary.zeroelem[i][0]==2)
		{
			for(j=1;j<=hungary.matrixsize;j++)
			{
    			if(hungary.zeroelem[0][j]!=2)
     				if(flag2==0)
     				{
     				 	min=hungary.cost[i][j];
      					flag2=1;
     				}
     			else
				{
      				if(hungary.cost[i][j]<min)
       					min=hungary.cost[i][j];
     			}
   			}        
  		}
 	}					//寻找未被覆盖的最小值 
	for(i=1;i<=hungary.matrixsize;i++)
	{
		if(hungary.zeroelem[i][0]==2)
			for(j=1;j<=hungary.matrixsize;j++)
				hungary.cost[i][j]=hungary.cost[i][j]-min;
	}
	for(j=1;j<=hungary.matrixsize;j++)
	{
		if(hungary.zeroelem[0][j]==2)
			for(i=1;i<=hungary.matrixsize;i++)
				hungary.cost[i][j]=hungary.cost[i][j]+min;
	}                   //未被划线的行减去未被覆盖的最小值,被划线的列加上未被覆盖的最小值 
	for(i=0;i<=hungary.matrixsize;i++)
		for(j=0;j<=hungary.matrixsize;j++)
			hungary.zeroelem[i][j]=0;              //矩阵清0
	circlezero(hungary); 
}
void output(int result[5041][2],MATRIX hungary)
{
	int num;	//解的数量 
	int minsum;	//最小的工作成本 
	int i,j;
	char w;
	int start;  //每个解的储存开始位置 
	minsum=0;
	for(i=1;i<=hungary.matrixsize;i++)
	{
		minsum=minsum+hungary.costforout[i][result[i][1]];
	}
	printf("最优解的目标函数值为%d.\n",minsum);
	num=result[0][0];
  	printf("有%d种解.\n",num);  
	getchar();
	for(i=1;i<=num;i++)
	{
		printf("按任意键输出第%d种解.\n",i);
		scanf("%c",&w);
		start=(i-1)*hungary.matrixsize+1;	 
		for(j=start;j<start+hungary.matrixsize;j++)
    			printf("第%d个人做第%d件工作.\n",result[j][0],result[j][1]);
 		printf("\n");
 	}
}

参考

Assignment Problem(任务分配问题) 详解
Cmd Markdown 公式指导手册
十分钟教你求解分配问题
匈牙利算法详解

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

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

相关文章

关联分析——apprior算法

1.txt文件的打开与关闭 2.list的操作 3.字典的创建及保存 4.txt文件的创建与写入 输入&#xff1a; 结果&#xff1a; import os#input min_sup4 max_item[] data [] transaction[]curent_transaction,current_sup[],[] result_transaction,result_sup[],[]#Storage resul…

线索二叉树操作详解(详细图例+cpp实现+源码)

文章目录线索二叉树中序线索二叉树构造线索二叉树节点的线索化其他操作销毁二叉搜索树获取中序遍历的第一个节点获取中序遍历的最后一个节点输出中序遍历序列逆序输出中序遍历序列源码线索二叉树 线索二叉树又称为二叉树的线索化。 在一个具有n个节点的二叉树中&#xff0c;它…

Linux零基础入门(一)初识Linux

Linux零基础入门&#xff08;一&#xff09;初识Linux前言操作系统概述一 操作系统概述1 硬件和软件2 操作系统二 初识Linux1 Linux的诞生2 Linux内核3 Linux发行版三 虚拟机介绍1 虚拟机四 VMware WorkStation安装1 虚拟化软件五 在VMware上安装Linux1 下载CentOS操作系统六 远…

[附源码]计算机毕业设计springboot体育馆场地预约管理系统

项目运行 环境配置&#xff1a; Jdk1.8 Tomcat7.0 Mysql HBuilderX&#xff08;Webstorm也行&#xff09; Eclispe&#xff08;IntelliJ IDEA,Eclispe,MyEclispe,Sts都支持&#xff09;。 项目技术&#xff1a; SSM mybatis Maven Vue 等等组成&#xff0c;B/S模式 M…

SwiftUI 如何快速识别视图(View)界面的刷新是由哪个状态的改变导致的?

功能需求 在 SwiftUI 中,我们视图的界面可能在不经意间被意外刷新了。这时,我们希望知道是该视图中的哪个状态导致了刷新。在包含众多状态的复杂视图中,这往往很难实现。 如上图所示,当我们随机改变视图中的状态时,可以在调试控制台中轻松看到是哪个状态导致了视图的刷新…

什么样的跨网数据摆渡系统,能够减少数据泄密的风险?

企业在公司正常运行下难免会产生一些重要数据或者敏感数据&#xff0c;这些都是企业在发展过程中积累下来的重要数据资产&#xff0c;对企业的发展至关重要。这些数据资产往往关联着企业的核心数据&#xff0c;一旦面临泄露&#xff0c;不仅仅会影响企业发展&#xff0c;甚至会…

词法分析(编译原理不用慌)

目录 一.简单版 二.简单版&#xff08;文本保存&#xff09; c版 运行结果&#xff1a; Java版 运行结果&#xff1a; 三.第三版&#xff08;文本保存&#xff09; c版 运行结果&#xff1a; 一.简单版 #include<stdio.h> #include<iostream> using namesp…

独立站SaaS系统站群模式怎么玩

做独立站的人都知道“站群”这个游戏&#xff0c;意思是通过建站工具一次性建好几百个或者几千个独立站。各个独立站卖的品类比较垂直&#xff0c;不会有太多SKU。销量好的站会留着精细化运营&#xff0c;没流量的就放弃。 使用脸书或谷歌和其他广告渠道来测试产品。每个产品…

Unity3d bounds包围盒 和collider碰撞器区别

Bounds 外包围盒 Bounds 叫作外包围盒、边界框、外扩矩形.是struct 结构体。而我们获得Bounds的主要途径有三种&#xff1a;Render,Collider,Mesh。 Render.bounds 世界坐标 Collider.bounds 世界坐标 Mesh.bounds 本地坐标 var m GetComponent<MeshFilter>().bound…

抖音用户浏览行为数据分析与挖掘

下文部分代码省略&#xff0c;完整项目代码及数据集链接&#xff1a;抖音用户浏览行为数据分析与挖掘 目录1.特征指标构建0. 项目介绍与说明**数据集说明**浏览行为1. 数据简单处理2. 特征指标构建用户指标分析&#xff1a;作者指标分析&#xff1a;作品指标分析&#xff1a;3.…

5分钟快速上手Nmap指令(基于Kali系统)

前言正文1、修改Kali系统中网络配置2、Nmap简介2.1 用途2.2优势2.3 相关知识3、Nmap中最常用的命令3.1 单主机扫描3.2 多目标扫描3.3 检测目标主机漏洞3.3 时序选择3.4 保存4、kali系统中常见报错参考文献前言 本篇为理论篇&#xff0c;主要为CTF攻防做铺垫&#xff0c;围绕 基…

[附源码]SSM计算机毕业设计影院售票系统JAVA

项目运行 环境配置&#xff1a; Jdk1.8 Tomcat7.0 Mysql HBuilderX&#xff08;Webstorm也行&#xff09; Eclispe&#xff08;IntelliJ IDEA,Eclispe,MyEclispe,Sts都支持&#xff09;。 项目技术&#xff1a; SSM mybatis Maven Vue 等等组成&#xff0c;B/S模式 M…

mac m1 mysqlworkbench8 Unknown table ‘COLUMN_STATISTICS‘

原因&#xff1a;本地mysql版本是8&#xff0c;远程是mariaDb-10&#xff0c;版本不匹配导致报错。 仔细看mysqlworkbench8.0导出时的错误信息&#xff0c;有mysqldump的具体路径。 mac os (m1, ventura系统)&#xff0c;具体位置是这里&#xff1a; /Applications/MySQLWor…

【树莓派开发日记1】1.3k预算的树莓派+显示屏+键鼠的选型与拆箱物理安装

树莓派开发日记1 经过了漫长的上课与考试周期&#xff0c;终于有时间闲下来进行技术栈的开发与学习 作为立志成为优秀机器人开发者的青年工程师&#xff08;青春版&#xff09;&#xff0c;不可能不去了解微机处理系统和Ubuntu系统&#xff0c;所以在此又给自己开了一个大坑 …

OpManager 帮助排查网络延迟问题

什么是网络延迟 网络中的延迟是指数据通过网络传输到其预期目的地所需的时间。它通常表示为往返延迟&#xff0c;即数据从一个位置传输到另一个位置所需的时间。 什么原因导致网络延迟 有四个主要原因会影响网络延迟。其中包括&#xff1a; 传输介质&#xff0c;例如 WAN 或…

JUC并发编程第六篇,带你了解Java内存模型JMM

JUC并发编程第六篇&#xff0c;带你了解Java内存模型JMM一、Java Memory Model&#xff08;Java内存模型&#xff09;是什么&#xff1f;二、JMM规范三大特性1. 可见性2. 原子性3. 有序性三、JMM规范下多线程对变量的读写过程四、JMM规范下多线程先行发生原则&#xff08;happe…

Oracle面试题整理

目录 Oracle面试题整理 1.MySQL和Oracle的区别&#xff1a; 2.Oracle中function和procedure的区别&#xff1f; 3. 比较truncate和delete命令 &#xff1f; 4.oralce中 rowid, rownum的定义 5. 事务的特性&#xff08;ACID&#xff09;是指什么 6. 列举几种表连接方式…

[附源码]计算机毕业设计springboot天狗电子商城系统

项目运行 环境配置&#xff1a; Jdk1.8 Tomcat7.0 Mysql HBuilderX&#xff08;Webstorm也行&#xff09; Eclispe&#xff08;IntelliJ IDEA,Eclispe,MyEclispe,Sts都支持&#xff09;。 项目技术&#xff1a; SSM mybatis Maven Vue 等等组成&#xff0c;B/S模式 M…

plink2.0和plink1.9的忧伤笔记

虽然plink2.0已经存在好久了&#xff0c;但是一直用的都是plink1.9&#xff0c;因为语法熟悉。更主要是plink2.0语法变动太大&#xff0c;害怕步子迈得太大了…… 今天看一下plink2.0的读入和输出数据常用参数&#xff0c; plink2.0用是不会用的&#xff0c;2022年都不会用&am…

计算机网络基础

前言 计算机网络学习的核心内容就是网络协议的学习。网络协议是为计算机网络中进行数据交换而建立的规则、标准或者说是约定的集合。因为不同用户的数据终端可能采取的字符集是不同的&#xff0c;两者需要进行通信&#xff0c;必须要在一定的标准上进行。一个很形象地比喻就是…