## [$AcWing$ $420$. 火星人](https://www.acwing.com/problem/content/description/422/)   ### 1.算法:$STL$ ```cpp {.line-numbers} #include using namespace std; const int N = 10010; int n, m; int a[N]; /* 5 3 1 2 3 4 5 答案 1 2 4 5 3 变化过程 (1) 1 2 3 5 4 (2) 1 2 4 3 5 (3) 1 2 4 5 3 */ int main() { cin >> n >> m; for (int i = 1; i <= n; i++) cin >> a[i]; while (m--) next_permutation(a + 1, a + 1 + n); // 输入数据保证这个结果不会超出火星人手指能表示的范围。 /* int a[4] = {1, 2, 3, 4}; sort(a, a + 4); do { for (int i = 0; i < 4; i++) cout << a[i] << " "; cout << endl; } while (next_permutation(a, a + 4)); */ for (int i = 1; i <= n; i++) printf("%d ", a[i]); return 0; } ``` ### 2 、算法:利用贪心法解决字典序最小相关问题: ![](https://dsideal.obs.cn-north-1.myhuaweicloud.com/HuangHai/BlogImages/{year}/{month}/{md5}.{extName}/202309181044220.png) ```cpp {.line-numbers} #include using namespace std; const int N = 10010; int q[N]; int n, m; int main() { cin >> n >> m; for (int i = 0; i <= n; i++) cin >> q[i]; while (m--) { // 执行 m次 int k = n - 1; // 从后向前来 /* Q:123654321 问下一个是啥? 算法步骤: 1、从向向前找第一个下降点,本例就是6 */ while (q[k - 1] > q[k]) k--; // 2、 k--:找到3 int t = k--; // 3、从3开始,向后找第一个大于3的数字,就是4 while (t + 1 < n && q[t + 1] > q[k]) t++; // 4、交换3和4 swap(q[t], q[k]); // 5、对于折点的后半部进行翻转,即 124 653321 =>翻转=> 124 123356 reverse(q + k + 1, q + n); } for (int i = 0; i < n; i++) printf("%d ", q[i]); return 0; } ```