标签:can 第一个字符 char 删除 gre scan ack memset set
题意:有个编辑器,支持三种操作,摁下一个键盘上的字符,重复最后一个单词,删除最后一个字符.给N个字符串,必须先在编辑器内输入第一个字符,
问,输入完所有字符串最少需要摁下多少次键盘.
最多100个字符串,每个字符串长度最多为100.
可以观察到,为了使摁下键盘的次数最少,必须尽可能的利用当前输入的最后一个字符串.考虑到俩个操作,重复最后一个字符串,删除最后一个字符,那么,只要前缀是匹配的,就可以通过这
俩个操作来减少摁下键盘的次数.所以每次都找前缀匹配最大的字符串即可.
老罗一定做过这个题,而且抄袭了这个创意,用语音控制输入.
#include <string> #include<iostream> #include<map> #include<memory.h> #include<vector> #include<algorithm> #include<queue> #include<vector> #include<stack> #include<math.h> #include<iomanip> #include<bitset> #include"math.h" namespace cc { using std::cout; using std::endl; using std::cin; using std::map; using std::vector; using std::string; using std::sort; using std::priority_queue; using std::greater; using std::vector; using std::swap; using std::stack; using std::bitset; constexpr int N = 110; int cases; char strs[N][N]; char cur[N]; int total = 0; int n; void solve() { cin >> cases; while (cases--) { cin >> n; total = 0; memset(strs,0,sizeof(strs)); for (int i=0;i<n;i++) { scanf("%s",strs[i]); } total += strlen(strs[0]); memcpy(cur,strs[0],sizeof(strs[0])); int vis[N] = {0}; int seqs[N] = {0}; int seq = 0; seqs[seq++] = 0; vis[0] = 1; while (true) { int nextIndex = -1; int min = -1; int curL = strlen(cur); for (int i=0;i<n;i++) { if (vis[i] != 0) continue; int curMin = 0; for (int j=0;j< curL;j++) { if (strs[i][j] == ‘\0‘|| strs[i][j]!= cur[j]) break; ++curMin; } if (min < curMin) { min = curMin; nextIndex = i; } } if (nextIndex == -1) break; vis[nextIndex] = 1; seqs[seq++] = nextIndex; total += strlen(strs[nextIndex])-min; memcpy(cur,strs[nextIndex],N); } cout << total << endl; for (int i = 0;i < n;i++) { cout << strs[seqs[i]] << endl; } } } }; int main() { #ifndef ONLINE_JUDGE freopen("d://1.text", "r", stdin); #endif // !ONLINE_JUDGE cc::solve(); return 0; }
标签:can 第一个字符 char 删除 gre scan ack memset set
原文地址:https://www.cnblogs.com/shuiyonglewodezzzzz/p/10292278.html