UVA11988:悲劇文本(模擬鏈表)


You’re typing a long text with a broken keyboard. Well it’s not so badly broken. The only problem with the keyboard is that sometimes the “home” key or the “end” key gets automatically pressed (internally). You’re not aware of this issue, since you’re focusing on the text and did not even turn on the monitor! After you finished typing, you can see a text on the screen (if you turn on the monitor). In Chinese, we can call it Beiju. Your task is to find the Beiju text.

Input
There are several test cases. Each test case is a single line containing at least one and at most 100,000 letters, underscores and two special characters ‘[’ and ‘]’. ‘[’ means the “Home” key is pressed internally, and ‘]’ means the “End” key is pressed internally. The input is terminated by end-of-file (EOF).
Output
For each case, print the Beiju text on the screen.

Sample Input

This_is_a_[Beiju]_text

[[]][][]Happy_Birthday_to_Tsinghua_University

Sample Output

BeijuThis_is_a__text

Happy_Birthday_to_Tsinghua_University

 

概譯:我們在用鍵盤輸入字符串,如果出現' [ '光標就跳到最前面,如果出現' ] '就跳到最后面,給出輸入時的字符串輸出實際得到的字符串,詳見樣例。

思路:水題輕噴……模擬,鏈表插入,可以用數組實現模擬鏈表。我模擬鏈表不太熟,第一次是用STL模擬的。可以用一個雙端隊列deque儲存最終結果,遇到一個' [ '就把后面的字符放在stack里,再遇到' [ '或' ] '時把stack里的字符放在deque的front里。PS:可能WA的數據:abc[123[456[ef

STL比較慢,100msAC

 1 #include <bits/stdc++.h>
 2 using namespace std;
 3 
 4 int main()
 5 {
 6     string s;
 7     while(getline(cin,s))
 8     {
 9         s+=']';
10         deque<char>dq;
11         stack<char>st;
12         bool state=false;
13 
14         for (int i = 0; s[i]; ++i)
15         {
16             if (s[i]=='[')    state=true;    
17             else if (s[i]==']')    state=false;
18             
19             if(state)   
20             {
21                 if(s[i]!='[')    
22                     st.push(s[i]);
23                 else
24                     while(!st.empty())
25                     {
26                         dq.push_front(st.top());
27                         st.pop();
28                     }
29             }
30             else
31             {
32                 if(s[i]!=']')
33                     dq.push_back(s[i]);
34                 while(!st.empty())
35                 {
36                     dq.push_front(st.top());
37                     st.pop();
38                 }
39             }     
40         }
41 
42         while(!dq.empty())
43         {
44             printf("%c",dq.front());
45             dq.pop_front();
46         }
47         printf("\n");
48     }
49     return 0;
50 }

 

模擬鏈表是用一個next數組代替鏈表中的next指針,比如第一個字符s[1]的下一個是s[2],則next[1]=2。思想上和鏈表是一樣的。另外眾所周知,鏈表的題常常會把第0個作為不儲存數據的輔助頭結點,第一個下標才開始儲存數據。

標程的思路是設置一個光標cur,但這個cur不是當前遍歷到的位置i,而代表着位置i的字符應該插入在cur的右側。期間cur有時會跳至左端即cur=0;有時要回到右端,所以還要開一個last變量保存最右端的下標,使cur=last跳回右端。

代碼更精簡,30ms,如下:

 1 #include <bits/stdc++.h>
 2 using namespace std;
 3 #define maxl 100005
 4 
 5 int main()
 6 {
 7     char s[maxl];
 8     while(~scanf("%s",s+1))
 9     {
10         int Next[maxl]={0};
11         int cur=0,last=0;
12 
13         for (int i = 1; s[i]; ++i)
14         {
15             if(s[i]=='[')    cur=0;
16             else if(s[i]==']')    cur=last;
17             else
18             {
19                 //鏈表插入操作
20                 Next[i]=Next[cur];
21                 Next[cur]=i;
22                 //last的更新
23                 if(cur==last)    last=i;
24                 //cur的更新
25                 cur=i;
26             }
27         }
28 
29         for (int i = Next[0]; i != 0; i = Next[i])
30             if (s[i]!='['&&s[i]!=']')
31                 printf("%c",s[i]);
32         printf("\n");    
33     }
34     return 0;
35 }

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM