题目大意:
只有swap(0,*)的操作,寻找排序到递增的最小的交换次数
输入:n=10
代表0-9这几个数字
题目思路:
1.利用数组保存输入的数据顺序;
2.
0对应的位置是几,和这个数字进行交换
若a[0]的值是0,则找到第一个不匹配的位置与0交换
终止条件为排序完成 (思路正确,但是代码实现比较复杂)
提交:
1.第一次提交超时,因为排序完成的判断每次都是循环全部,可以在查找第一个不匹配的位置时候判断是否排序完毕
2.观看算法笔记,对于数字的查找,可以直接从有序数字后面开始,节省时间
再次查看算法笔记,数组保存的是该数字的位置,这样数组0代表的就是0的位置,0存储在哪里,可以省去查找0的代码
用变量k保存已经有序的位置,i到n,则代表全部有序,代表退出循环
如果a[0]不是0则替换0和在0这个位置上的数字
收获
1.可以用数字保存数字下标i对应的这个数的位置,可以省去查找这个数的时间
2.可以用k保留目前已经有序的位置,防止一直从头开始检测
#include <iostream>
#include<string>
#include<stdlib.h>
#include<stdio.h>
#include<string.h>
#include<algorithm>
#include<vector>
//Be Unique permutation置换
//Sort with Swap(0, i)
/*
题目大意:
只有swap(0,*)的操作,寻找排序到递增的最小的交换次数
输入:n=10
代表0-9这几个数字
题目思路:
1.利用数组保存输入的数据顺序;
2.
0对应的位置是几,和这个数字进行交换
若a[0]的值是0,则找到第一个不匹配的位置与0交换
终止条件为排序完成
提交:
1.第一次提交超时,因为排序完成的判断每次都是循环全部,可以在查找第一个不匹配的位置时候判断是否排序完毕
2.观看算法笔记,对于数字的查找,可以直接从有序数字后面开始,节省时间
再次查看算法笔记,数组保存的是该数字的位置,这样数组0代表的就是0的位置,0存储在哪里,可以省去查找0的代码
用变量k保存已经有序的位置,i到n,则代表全部有序,代表退出循环
如果a[0]不是0则替换0和在0这个位置上的数字
*/
int find(int *a,int k,int n,int b)
{
for(int i=k;i<n;i++)
{
if(a[i]==b)
return i;
}
}
using namespace std;
int main() {
int n;
cin>>n;
int *a=(int *)malloc(sizeof(int)*n);
for(int i=0;i<n;i++)
{
int input;
cin>>input;
a[input]=i;//数组下标表示那个数字,i代表这个数字现在在哪里
};
int sum=0;
int k=1;
while(1)
{
if(a[0]!=0)
{
swap(a[0],a[a[0]]);
sum++;
}
else
{
int i;
for(i=k;i<n;i++)
{
if(a[i]!=i)
{
k=i;
swap(a[0],a[i]);
sum++;
break;
}
}
if(i==n)break;
}
/* for(int i=0;i<n;i++)
cout<<a[i]<<" ";*/
//cout<<endl;
}
cout<<sum<<endl;
/*int n;
cin>>n;
int *a =(int *)malloc(sizeof(int)*n);
for(int i=0;i<n;i++)
{
scanf("%d",&a[i]);
}
int sum=0;
bool right=false;
int first=0;
while(right==false)
{ int k=find(a,0,n,0);//查找0的位置
int h=find(a,0,n,k);//查找0对应数字的位置
if(k==0)
{
int j;
for( j=1;j<n;j++)
{
if(a[j]!=j)
{
swap(a[0],a[j]);
first=j;
break;
}
}
if(j==n)
{
right=true;
break;
}
}
else
swap_a(&a[k],&a[h]);
sum++;
}
cout<<sum<<endl;*/
system("pause");
}