【做题】sgu189 Perl-like Substr——dark模拟

注:这篇博客纯属为凑篇数而生。

题面较长,幸运的是,网上给出了相当不错的翻译

需要支持的操作很简单,即对子串提取、赋值和输出,且对时间复杂度没有要求。换言之此题有成为块链毒瘤题的潜质。难点在于输入的格式是类似于源代码的,但形式单一,变量前均有$字符标注,可以通过直接判断来解决。于是就只需要大力讨论就可以了。

这或许就是所谓的题意即题解吧。

时间复杂度O(m*l)。

  1 #include <bits/stdc++.h>
  2 using namespace std;
  3 const int N = 110, LN = 25;
  4 string var[N], tmp, tp;
  5 int node[N * LN][63], tag[N * LN], cnt, tot = 1, pos;
  6 inline int read() {
  7   int res = 0; bool key = 0;
  8   for (; !(tmp[pos] >= '0' && tmp[pos] <= '9') ; ++ pos)
  9     key = (tmp[pos] == '-');
 10   for (; tmp[pos] >= '0' && tmp[pos] <= '9' ; ++ pos)
 11     res = (res << 3) + (res << 1) + tmp[pos] - '0';
 12   if (key) res = - res;
 13   return res;
 14 }
 15 inline int get_val(char x) {
 16   if (x >= '0' && x <= '9') return x - '0';
 17   if (x >= 'a' && x <= 'z') return x - 'a' + 10;
 18   if (x >= 'A' && x <= 'Z') return x - 'A' + 36;
 19   return -1;
 20 }
 21 inline bool invar(char x) {
 22   return (x >= '0' && x <= '9') || (x >= 'a' && x <= 'z') || \
 23     (x >= 'A' && x <= 'Z') || x == ' ' || x == ',' || x == '.' || \
 24     x == '-' || x == '_' || x == ':' || x == '!' || x == '?';
 25 }
 26 int find(string s) {
 27   int l = s.length(), p = 1, t;
 28   for (int i = 0 ; i < l ; ++ i) {
 29     t = get_val(s[i]);
 30     if (!node[p][t]) node[p][t] = ++ tot;
 31     p = node[p][t];
 32   }
 33   if (!tag[p]) {
 34       tag[p] = ++ cnt;
 35       var[cnt] = "";
 36     }
 37   return tag[p];
 38 }
 39 int get_tag() {
 40   tp = "";
 41   while (~get_val(tmp[++ pos]))
 42     tp += tmp[pos];
 43   return find(tp);
 44 }
 45 void solve_init() {
 46   int l = tmp.length(), p;
 47   tp = "";
 48   for (pos = 0 ; pos < l ; ++ pos) {
 49     if (tmp[pos] == '$') {
 50       var[p = get_tag()] = "";    
 51       break;
 52     }
 53   }
 54   while (tmp[pos] != '"') ++ pos;
 55   for (++ pos ; invar(tmp[pos]) ; ++ pos) {
 56     var[p] += tmp[pos];
 57   }
 58 }
 59 void subst(int& p,int& l,int& n) {
 60   while (tmp[pos] != '$') ++ pos;
 61   p = get_tag();
 62   int len = var[p].length(), be, co;
 63   be = read();
 64   while (tmp[pos] != ',' && tmp[pos] != ')') ++ pos;
 65   if (tmp[pos] == ')') co = 0;
 66   else co = read();
 67   l = be >= 0 ? be : len + be;
 68   n = co >= 0 ? co > 0 ? co : len - l : len + co - l;
 69   while (tmp[pos] != ')') ++ pos;
 70   ++ pos;
 71 }
 72 void print() {
 73   while (tmp[pos] != '$' && tmp[pos] != 's') ++ pos;
 74   int p,l,n;
 75   if (tmp[pos] == '$') {
 76     p = get_tag();
 77     cout << var[p] << endl;
 78   } else {
 79     subst(p,l,n);
 80     cout << var[p].substr(l,n) << endl;
 81   }
 82   while (tmp[pos] != ')') ++ pos;
 83   ++ pos;
 84 }
 85 void solve() {
 86   int l = tmp.length(), p1, p2, l1, n1, l2, n2, t1, t2;
 87   for (pos = 0 ; tmp[pos] == ' ' ; ++ pos);
 88   switch(tmp[pos]) {
 89   case 's':subst(p1,l1,n1), t1 = 1; break;
 90   case 'p':print(); return;
 91   case '$':p1 = get_tag(), t1 = 0; break;
 92   }
 93   for (; tmp[pos] != '$' && tmp[pos] != 's' ; ++ pos);
 94   switch(tmp[pos]) {
 95   case 's':subst(p2,l2,n2), t2 = 1; break;
 96   case '$':p2 = get_tag(), t2 = 0; break;
 97   }
 98   if ((!t1) && (!t2)) var[p1] = var[p2];
 99   else if ((!t1) && t2) var[p1] = var[p2].substr(l2,n2);
100   else if (t1 && (!t2)) var[p1].replace(l1,n1,var[p2]);
101   else if (t1 && t2) var[p1].replace(l1,n1,var[p2],l2,n2);
102 }
103 int main() {
104   int n,m;
105   scanf("%d%d\n",&n,&m);
106   for (int i = 1 ; i <= n ; ++ i) {
107     getline(cin,tmp);
108     solve_init();
109   }
110   for (int i = 1 ; i <= m ; ++ i) {
111     getline(cin,tmp);
112     solve();
113   }
114   return 0;
115 }

 

小结:续了一个下午……代码能力不够的问题。

posted @ 2018-02-09 18:11  莫名其妙的aaa  阅读(159)  评论(0编辑  收藏  举报