【LeetCode-955】解题报告(暴力,贪心)

原始题目

给定由  N  个小写字母字符串组成的数组  A,其中每个字符串长度相等。

选取一个删除索引序列,对于  A  中的每个字符串,删除对应每个索引处的字符。

比如,有  A = ["abcdef", "uvwxyz"],删除索引序列  {0, 2, 3},删除后  A  为["bef", "vyz"]。

假设,我们选择了一组删除索引  D,那么在执行删除操作之后,最终得到的数组的元素是按 字典序(A[0] <= A[1] <= A[2] ... <= A[A.length - 1])排列的,然后请你返回  D.length  的最小可能值。

解题思路

  1. 裸枚举

    对于每个位置,判断整体是否符合字典序,复杂度\(O(WN^{2})\)

  2. 贪心

    对于每个间隔位置,用一个 vis 数组保存前面序列是否出现\(A[i-1][j] < A[i][j]\)

    遍历每个位置,不用判断整体字符串,只需考虑新加入的列,结合 vis 数组,如何结合?

    • \(vis[i] = 0\),表明之前间隔两边合法字符总是相同字符(反序字符列可以证明被删除),对于当前新加入的列,分三种情况,若出现正序,则更新为\(vis[i]=1\);若相等,保持\(vis[i]=0\);若出现反序,删除列,保持\(vis[i]=0\)
    • \(vis[i]=1\),表明之前间隔两边出现至少一次正序,那该间隔无需再考虑,间隔将题目要求分割到不同段的子要求。

解题代码

  • 裸枚举
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
typedef unsigned long long ull;
typedef pair<int, int> pii;
typedef pair<string, string> pss;
typedef vector<int> vi;
typedef vector<string> vs;

#define rep(i, a, n) for (int i = a; i < n; ++i)
#define per(i, a, n) for (int i = n - 1; i >= a; --i)
#define all(x) x.begin(), x.end()
#define mp make_pair
#define pb push_back
#define np next_permutation
#define fi first
#define se second

bool compare(vector<string>& A)
{
rep(i, 1, A.size())
{
if (A[i - 1] > A[i]) {
return false;
}
}
return true;
}

class Solution {
public:
int minDeletionSize(vector<string>& A)
{
vector<string> test(A.size(), "");
int ans = 0;
rep(i, 0, A.front().size())
{
rep(j, 0, A.size())
{
test[j].pb(A[j][i]);
}
if (!compare(test)) {
ans++;
rep(j, 0, A.size())
{
test[j].pop_back();
}
}
}
return ans;
}
};
  • 贪心
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
class Solution {
public:
int minDeletionSize(vector<string>& A)
{
int ans = 0;
vi pos(A.size(), 0);
rep(i, 0, A.front().size())
{
int flag = 0;
rep(j, 1, A.size())
{
if (!pos[j] && A[j][i] < A[j - 1][i]) {
ans++;
flag = 1;
break;
}
}
if (flag)
continue;
rep(j, 1, A.size())
{
if (A[j - 1][i] < A[j][i]) {
pos[j] = 1;
}
}
}
return ans;
}
};

收获与反思

暂无