您的位置:首页 > 其它

ACM选修(栈与队列)

2015-06-10 19:13 441 查看
数字符号串->整数

//数字符号串存于exp数组中
int factor=0;
do
{//合并出运算对象的值
factor=factor*10+exp[i]-48;
i=i+1;
}while(isdigit(exp[i]));


括号匹配的检验

假设表达式中充许括号嵌套,则检验括号是否匹配的方法可用“期待的急迫程度”这个概念来描述。例:{ ( [ ……]…)…{ (……)……} }  

括号配对检查程序

执行过程中栈的变化:  #{ ( [ ……]…)…{ (……)……} }# 

 
[            
(
{
#
输入格式:一行一个括号序列,可以输入若干行

输出格式:一行一个输出结果,配对为YES,不配对为NO

样例:

输入样例:

{ ( [  ] ) ( ) [ ] }

[ ( ) ] ( ) { ( ) }

{()}[]])

输出样例

YES

YES

NO
/*括号配对*/

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

int fun(char *);

int main()
{
char str[100];
cin>>str;

if(fun(str)==0)
cout<<"NO"<<endl;
else
cout<<"YES"<<endl;

return 0;
}

int fun(char *str)
{
unsigned int len;
int i=0;
stack<char>ch;
len=strlen(str);

for(i=0;i<len;i++)
switch(str[i])
{
case '(':
case '[':
case '{':ch.push (str[i]);
break;
case ')':if(ch.size ()==0)
return 0;
else
if(ch.top ()=='(')
ch.pop();
else
return 0;
break;
case ']':if(ch.size ()==0)
return 0;
else
if(ch.top ()=='[')
ch.pop();
else
return 0;
break;
case '}':if(ch.size ()==0)
return 0;
else
if(ch.top ()=='{')
ch.pop();
else
return 0;
break;
default:return 0;
}

if(ch.size ()==0&&i==len)
return 1;
else
return 0;
}

数制转换

十进制N和其它进制数的转换是计算机实现计算的基本问题,其解决方法很多,其中一个简单算法基于原理: N=(n / d)*d+n % d

输入格式

若干行,每行两个数据,分别表示要转换的十进制数以及所要转换成的进制(2~9)。

输出格式

每行一个输出结果,即转换出来的结果

输入输出格式样例:

输入

10 2

10 8

10 5

输出

1010

12

20

例如(1348)10=(250
4000
4)8,其运算过程如下:  

nn/8n%8
13481684
168210
2125
202
#include<stack>
#include<iostream>
using namespace std;
void main()
{ int n;
stack<int> st;
cin>>n;
while(n!=0) {st.push(n%8);n=n/8;}
while( !st.empty( ) ) {cout<<st.top();st.pop();}
return;
}


表达式的计算

1.后缀表达式的计算:

输入格式:一行一个后缀表达式,可以输入若干行

输出格式:一行一个输出结果

样例:

输入样例:

2 3 + 4*

6 2 / 3 *

输出样例

2 3 + 4*=20

6 2 / 4 *=12 

/*后缀表达式的计算*/

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

int main()
{
int n=0;
int temp=0;
unsigned int i;
char str[500];
stack<int>num;
gets(str);

for(i=0;i<strlen(str);)
switch(str[i])
{
case '0':
case '1':
case '2':
case '3':
case '4':
case '5':
case '6':
case '7':
case '8':
case '9':temp=temp*10+str[i]-'0';
i++;
break;
case ' ':if(str[i-1]<='9'&&str[i-1]>='0')
{
num.push (temp);
temp=0;
}
i++;
break;
case '+':n=num.top ();
num.pop ();
n=num.top ()+n;
num.pop ();
num.push (n);
i++;
break;
case '*':n=num.top ();
num.pop ();
n=num.top ()*n;
num.pop ();
num.push (n);
i++;
break;
case '-':n=num.top ();
num.pop ();
n=num.top ()-n;
num.pop ();
num.push (n);
i++;
break;
case '/':n=num.top ();
num.pop ();
n=num.top ()/n;
num.pop ();
num.push (n);
i++;
break;
}

cout<<n<<endl;

return 0;
}

2.中缀表达式转换为后缀表达式:
输入格式:一行一个中缀表达式,可以输入若干行

输出格式:一行一个,输出相应的后缀表达式

样例:

输入样例:

2+(3 + 4)*5

16+ 2 * 30 /4

输出样例

2  3  4 + 5 * +

16  2  30 * 4 /  +

/*中缀转换为后缀*/

#include<iostream>
#include<stack>
#include<queue>
using namespace std;

int main()
{
stack<char>ch;
queue<char>num;
unsigned int i;
char str[100];

cout<<"请输入中缀表达式:";
cin>>str;

for(i=0;i<strlen(str);i++)
switch(str[i])
{
case '0':
case '1':
case '2':
case '3':
case '4':
case '5':
case '6':
case '7':
case '8':
case '9':num.push (str[i]);break;
case '*':
case '/':num.push(' ');
ch.push (str[i]);break;
case '(':ch.push (str[i]);break;
case '+':
case '-':num.push (' ');
if(ch.size ()!=0)
while(ch.top ()=='*'||ch.top ()=='/')
{
num.push(ch.top());
ch.pop();
num.push (' ');
if(ch.size ()==0) break;
}
ch.push (str[i]);
break;
case ')':num.push(' ');
while(ch.top ()!='(')
{
num.push (ch.top ());
ch.pop ();
if(ch.top ()!='(')
num.push (' ');
}
ch.pop ();
break;
}

cout<<"后缀表达式为:";

while(ch.size ())
{
num.push(' ');
num.push(ch.top());
ch.pop();
}

while(num.size ())
{
cout<<num.front ();
num.pop ();
}

cout<<endl;
return 0;
}

3.中缀表达式的计算:

输入格式:一行一个中缀表达式,可以输入若干行

输出格式:一行一个输出结果

样例:

输入样例:

2*(3 + 4)

6+ 2 * 3 /4

输出样例

2*(3 + 4)

6+ 2 * 3 /4

/*中缀表达式的计算*/

#include<iostream>
#include<stack>
#include<queue>
using namespace std;

int fun(char *,int );

int main()
{
stack<char>ch,result;
queue<char>num;
unsigned int i;
int n=0,temp=0;
char str[100],res[200];

cout<<"请输入中缀表达式:";
cin>>str;

for(i=0;i<strlen(str);i++)
switch(str[i])
{
case '0':
case '1':
case '2':
case '3':
case '4':
case '5':
case '6':
case '7':
case '8':
case '9':num.push (str[i]);break;
case '*':
case '/':num.push(' ');
ch.push (str[i]);break;
case '(':ch.push (str[i]);break;
case '+':
case '-':num.push (' ');
if(ch.size ()!=0)
while(ch.top ()=='*'||ch.top ()=='/')
{
num.push(ch.top());
ch.pop();
num.push (' ');

if(ch.size ()==0)
break;
}
ch.push (str[i]);
break;
case ')':num.push(' ');
while(ch.top ()!='(')
{
num.push (ch.top ());
ch.pop ();

if(ch.top ()!='(')
num.push (' ');
}
ch.pop ();
break;
}

while(ch.size ())
{
num.push(' ');
num.push(ch.top());
ch.pop();
}

for(i=0;num.size ()!=0;i++)
{
res[i]=num.front ();
num.pop ();
}

cout<<fun(res,i-1)<<endl;
return 0;
}

int fun(char *string,int len)
{
int n=0,temp=0;
unsigned int i;
stack<int>result;

for(i=0;i<=len;)
switch(string[i])
{
case '0':
case '1':
case '2':
case '3':
case '4':
case '5':
case '6':
case '7':
case '8':
case '9':temp=temp*10+string[i]-'0';
i++;break;
case ' ':if(string[i-1]<='9'&&string[i-1]>='0')
{
result.push (temp);
temp=0;
}
i++;break;
case '+':n=result.top ();
result.pop ();
n=result.top ()+n;
result.pop ();
result.push (n);
i++;break;
case '*':n=result.top ();
result.pop ();
n=result.top ()*n;
result.pop ();
result.push (n);
i++;break;
case '-':n=result.top ();
result.pop ();
n=result.top ()-n;
result.pop ();
result.push (n);
i++;break;
case '/':n=result.top ();
result.pop ();
n=result.top ()/n;
result.pop ();
result.push (n);
i++;break;
}

return n;
}

设有一个表L=(a1,a2,a3,…an),其中L为表名,a1,a2,…an为表中元素,当ai为数值时,表示一个元素值;当ai为大写字母时,表示另一个表,但不能循环定义。例如,

L=(3,4,8,S,9,0,8,T)

S=(10,3,4,U,9,6)

T=(4,5,6)

U=(7,9,8,6)

当给出全部表后,求出所有元素的最大元素。

输入格式

3,4,8,S,9,0,8,T

10,3,4,U,9,6

4,5,6

7,9,8,6

输出格式

10

void main()
{
queue<char> qu;
char str[255];
int i,s, max=-32767;
qu.push('A');
while(!qu.empty())
{
qu.pop();
cin.getline(str,255);
i=0;
while(str[i]!='\0')
{
if (isdigit(str[i]))
{
s=0;
do{s=s*10+str[i]-48;i++;}while (isdigit(str[i]));
if (s>max) max=s;
}
else if ( isalpha(str[i])) {qu.push(str[i]);i++;}
else i++;
}
}
cout<<max;
}


家族关系

有一个大家族,目前存在着如下的关系,其中A是最年长的族长,如果给出双亲与孩子之间的关系,请计算出该家族是属于几代同堂的。

A有孩子B、C和D

B有孩子E、F和G

C有孩子H和I……

输入格式

3  1 2 3

3  4 5 6

2  7 8

4  9 10 11 12

0

0

0

0

2  13 14

0

0

输出:

4

#include<iostream>
#include<queue>
using namespace std;
struct queuenode
{
int child;
int level;
};
int generate(int root)
{
queue<queuenode> qu;
queuenode temp,newtemp;
int child_num,child,i,maxlevel=0;

temp.child=root;
temp.level=1;

qu.push(temp);

while(!qu.empty())
{
temp=qu.front(); 	 qu.pop();
if (temp.level>maxlevel) maxlevel=temp.level;
cin>>child_num;
for(i=0;i<child_num;i++)
{
cin>>child;
newtemp.child=child;
newtemp.level=temp.level+1;
qu.push(newtemp);
}
}
return maxlevel;
}


问题:机器调度

考察一个机械厂,其中有m台一模一样的机器。现有n个作业需要处理,设作业i的处理时间为ti,这个时间为从将作业放入机器直到从机器上取下作业的时间。所谓调度(schedule)是指按作业在机器上的运行时间对作业进行分配,使得:

一台机器在同一时间内只能处理一个作业。

一个作业不能同时在两台机器上处理。

作业i一旦运行,则需要ti个时间单位。

例如,在一个C/C++程序中有如下嵌套调用的主函数main( )和三个函数f1( ),f2( ),f3( ):七个作业在三台机器上进行调度的情形,七个作业所需时间分别为(2, 14,4, 16, 6, 5, 3)。三台机器分别被编号为M1、M2和M3。

Task: 确定如何进行调度才能使在m台机器上执行给定的n个作业时所需要的处理时间最短

Solution:采用一个称为最长处理时间优先(Longest Processing Time first, LPT)的简单调度策略,在LPT算法中,

(1)作业按它们所需处理时间的递减顺序排列,即生成最大优先队列。

(2)由于在分配一个作业时,总要将其分配给最先变为空闲的机器,因此机器也按空闲的到来时刻生成一个最小优先队列,看谁快进入空闲状态。

问题

在一个序列中依次找出最小的两个值,并将它们的和值放入序列中,而将它们去掉,反复执行如此操作,直到剩下一个元素位置,最后输出该元素值以及整个选择过程。

输入输出样例:

输入:

6 6 2 3 3 4 9

输出

2 3  5

3 4  7

5 6 11

7 9 16

11 16 27

#include <queue>
#include <iostream>
using namespace std;

struct node
{	  int data;
node(int i) { data=i; }
};

bool operator<(const node &a,const node &b)
{	if(a.data>b.data ) return true;  else   return false;	}

int main()  {
node x(0);
priority_queue<node> p;
p.push(node(3));	p.push(node(9));	p.push(node(5));
while( !p.empty( ) ) {   x=p.top();    p.pop();  cout<<x.data<<" ";	}
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: