您的位置:首页 > 编程语言 > C语言/C++

ZOJ Problem Set - 1016 Parencodings

2017-11-27 20:48 369 查看
Parencodings
Time Limit: 2 Seconds      Memory Limit: 65536 KB

Let S = s1 s2 ... s2n be a well-formed string of parentheses. S can be encoded in two different ways:

By an integer sequence P = p1 p2 ... pn where pi is the number of left parentheses before the ith right parenthesis in S (P-sequence).
By an integer sequence W = w1 w2 ... wn where for each right parenthesis, say a in S, we associate an integer which is the number of right parentheses counting from the matched left parenthesis of a up to a. (W-sequence).
Following is an example of the above encodings:

S (((()()())))

P-sequence 4 5 6666

W-sequence 1 1 1456

Write a program to convert P-sequence of a well-formed string to the W-sequence of the same string.

Input

The first line of the input contains a single integer t (1 <= t <= 10), the number of test cases, followed by the input data for each test case. The first line of each test case is an integer n (1 <= n <= 20), and the second line is the P-sequence of a well-formed
string. It contains n positive integers, separated with blanks, representing the P-sequence.

Output

The output consists of exactly t lines corresponding to test cases. For each test case, the output line should contain n integers describing the W-sequence of the string corresponding to its given P-sequence.

Sample Input

2

6

4 5 6 6 6 6

9

4 6 6 6 6 8 9 9 9

Sample Output

1 1 1 4 5 6

1 1 2 4 5 1 1 3 9

Source: Asia 2001, Tehran (Iran)

题目大意:

把P编码转为W编码。

P编码的每个数字记录的是左边有多少个左括号

W编码的每个数字记录的是左边遇到的和它相匹配的左括号时经过的左括号个数

解题思路:

用堆栈来解题。每一次输入P的一位数字的时候,用堆栈来模拟括号,其中-1表示左括号,1表示右括号。每次输入P的一位数字之后,我们将这么多位左括号(-1)入栈,判断栈顶为1还是-1,如果为-1则W输出1,否则持续出栈直到遇到-1,则输出累加的数字+1。

AC:

#include <cstdio>
#include <string>
#include <stack>
#include <iostream>
using namespace std;

stack<int> S;

int main()
{
int N;
cin>>N;
while(N--)
{
int n;
cin>>n;
int p;
int t = 0;//记录已经输入的左括号数(当前P的前序)
for(int i = 1; i <= n; i++)
{
cin>>p;
for(int j = 1; j <= p - t; j++)
S.push(-1); //将左括号全部入栈
if(S.top() == -1) //判断,如果栈顶元素为-1,则输出1
{
i == 1 ? cout<<"1" : cout<<" 1";
S.pop(); //并出栈-1,入栈1
S.push(1);
}
else //如果栈首不是-1,则开始计算前面有多少对括号
{
int iTop = S.top();//直接出栈栈首
S.pop();
while(S.top() != -1)//持续pop,直到遇到-1
{
iTop += S.top();
S.pop();
}
cout<<" "<<iTop + 1;
S.pop();
S.push(iTop + 1);
}
t = p;
}
cout<<endl;
while(!S.empty())
S.pop();
}
system("pause");
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  C++ 算法