1067. Sort with Swap(0,*) (25)
来源:互联网 发布:知乎 张艺兴 编辑:程序博客网 时间:2024/06/03 18:59
Given any permutation of the numbers {0, 1, 2,…, N-1}, it is easy to sort them in increasing order. But what if Swap(0, *) is the ONLY operation that is allowed to use? For example, to sort {4, 0, 2, 1, 3} we may apply the swap operations in the following way:
Swap(0, 1) => {4, 1, 2, 0, 3}
Swap(0, 3) => {4, 1, 2, 3, 0}
Swap(0, 4) => {0, 1, 2, 3, 4}
Now you are asked to find the minimum number of swaps need to sort the given permutation of the first N nonnegative integers.
Input Specification:
Each input file contains one test case, which gives a positive N (<=105) followed by a permutation sequence of {0, 1, …, N-1}. All the numbers in a line are separated by a space.
Output Specification:
For each case, simply print in a line the minimum number of swaps need to sort the given permutation.
Sample Input:
10 3 5 7 2 6 4 9 0 8 1
Sample Output:
这里我先贴一下我写的程序吧,但是两个测试点超时了。
#include<bits/stdc++.h>using namespace std;int sum;int xiugai(vector<int> &jt, int n){ int i; int temp; for (i = 1; i < n ; i++) { if (jt[i] != i) break; } if (i == n) { cout << sum; exit(0); } else { temp = jt[i]; jt[i] = 0; jt[0] = temp; sum ++; } return i;}int main(void){ int n; cin >> n; if (n == 0) { cout << "0"; return 0; } vector<int> jt(n); int i, temp; for (i = 0; i < n; i++) { cin >> jt[i]; } if (jt[0] == 0) { for (i = 1; i < n ; i++) { if (jt[i] != i) break; } if (i == n) { cout << sum; return 0; } else { temp = jt[i]; jt[i] = 0; jt[0] = temp; sum ++; } } int index1, tmp, index2; for (i = 0; i < n; i++) { if (jt[i] == 0) break; } if (i == 0) { index1 = xiugai(jt, n); tmp = index1; } else { index1 = i; tmp = i; } for (i = 0; i < n; i++) { if (jt[i] == tmp) break; } index2 = i; jt[index2] = 0; jt[index1] = tmp; sum++; for(;;) { if (index2 == 0) { index1 = xiugai(jt, n); tmp = index1; } else { index1 = index2; tmp = index2; } for (i = 0; i < n; i++) { if (jt[i] == tmp) break; } index2 = i; jt[index1] = tmp; jt[index2] = 0; sum++; if (i == n) { cout << sum; break; } } return 0;}/* 10 9 8 7 6 5 4 3 2 1 0*/
为什么会超时呢,原因是,我存储数据的方式是数组下标表示位置,数组元素表示对应位置上的元素。这样一来,每次要去找对应位置的时候(这里算法不仔细分析了,如果连算法都还没想出来的建议去看看别人的博客),就得从第0个位置找到最后一个元素,找出来0所在位置应该在的元素,它的位置在哪里,每次查找需要O(N)复杂度,总共有O(N)个点,所以总的复杂度花了O(N^2),所以有两个点超时。
那么怎么解决呢,这里贴下别人的代码:
#include <stdio.h> int findNotOK(int* arr,int begin,int end) //从begin开始往后寻找未到位的数 { for(int i=begin;i<end;i++) { if(arr[i]!=i)return i; } return 0; } int main() { int n; scanf("%d",&n); int* arr = new int[n]; int i,t; for(i=0;i<n;i++) { scanf("%d",&t); arr[t]=i; } int tmp = 0; int count=0; int firstPos = 1; firstPos = findNotOK(arr,firstPos,n); while(firstPos) //还有未到位的数字 { if(arr[0]==0) //如果0到位了,则与未到位的firstPos交换 { arr[0] = arr[firstPos]; arr[firstPos] = 0; count++; } while(arr[0]!=0) //如果0不到位,则循环与自己所指向的值交换 { tmp = arr[0]; arr[0] = arr[tmp]; arr[tmp] = tmp; count++; } firstPos = findNotOK(arr,firstPos,n); //此时0归位了,找到下一个未到位的数字 } printf("%d\n",count); return 0; }
我看那个博主并没有对这种存储方式的优点和原因进行分析,所以我这里帮他分析一下。
这里存储我感觉就像是一个哈希表,实际上是一个map。但是c++ map虽然容易理解,但是太容易超时,而且反正只是int -> int的一个映射,直接用基本的数组就可以了.
这里是这么存储数据的:下标表示那个元素,数组元素表示位置,也就是说,比如给一组数据3, 2 1 0
那么就是arr[2] = 0,意思是数字2,它现在的位置是在0。
所以,这个方式的好处就是,你不需要查找了,你直接比如说想知道,5这个元素,它的位置在哪里,你直接arr[5]就直接获得了它的位置。
比如说6个数:6, 1 2 3 4 5 0 现在按照算法,你是要把这列数字的0和5进行一个交换,变成123405,对吧。
那么你直接先找到arr[0] = 5,我们直接找到0现在在数列的第6个地方,然后再temp = arr[0]
,然后再arr[temp]直接找到5这个数在数列的第五个地方,那么我们直接交换,arr[0] = arr[temp],arr[temp] = temp,这样就实现了我们位置的交换。
现在对数据结构的理解越来越深刻了,一个好的数据存储方式,直接导致了你的代码所需要的算法更简单。就像这位博主的代码,我们往往正常思维,数组下标表示位置,数组元素表示你需要存储的数据,但是这里用下标表示你要存储的数据,数组元素来表示位置,这就是代码思维和数据结构的魅力所在吧!
- 1067. Sort with Swap(0,*) (25)
- 1067. Sort with Swap(0,*) (25)
- 1067. Sort with Swap(0,*) (25)
- pat 1067. Sort with Swap(0,*) (25)
- 1067. Sort with Swap(0,*) (25)
- 1067. Sort with Swap(0,*) (25)
- 1067. Sort with Swap(0,*) (25)
- 1067. Sort with Swap(0,*) (25)
- 1067. Sort with Swap(0,*) (25)
- 1067. Sort with Swap(0,*) (25)
- 1067. Sort with Swap(0,*) (25)
- PAT 1067. Sort with Swap(0,*) (25)
- 1067. Sort with Swap(0,*) (25)
- 1067. Sort with Swap(0,*) (25)
- 1067. Sort with Swap(0,*) (25)
- 【PAT】1067. Sort with Swap(0,*) (25)
- 1067. Sort with Swap(0,*) (25)
- 1067. Sort with Swap(0,*) (25)
- ctf常见php弱类型分析
- UVA 10881
- filebeat multiline配置
- phpstudy域名站点设置
- Spring Boot -- Controller之Validate参数校验
- 1067. Sort with Swap(0,*) (25)
- Java并发编程:(3)synchronized和Lock
- Linux常用命令
- 为什么tcp没有长度,而udp有
- HDU 2602
- [wordpress & nginx]除了homepage其他子页面全是404 not found
- web安全:QQ号快速登录漏洞及被盗原理
- Dubbo初体验:远程服务调用和管控台的搭建
- php涉及金额计算用bc函数比较准