题目
正确性已验证:
需要看日志则取消 #define log 的注释
#include <bits/stdc++.h>
using namespace std;
#define int long long
//#define Log //日志开关
bool isLoop = false;
struct Gate{
#ifdef Log
string name;
#endif
vector<Gate* > inputs;
bool output;
string func;
bool calculated;
bool visited;
bool getOutput(){
#ifdef Log
cout << "calculating " << name << endl;
#endif
if(calculated){ //如果算过了就直接返回该结果
#ifdef Log
cout << "calculated! output = " << output << endl;
#endif
return output;
}else if(visited){ //如果该门访问过但是没计算出结果->出现环了
#ifdef Log
cout << "visited! there are a loop" << endl;
#endif
isLoop = true;
return false;
}else{
visited = true;//标记该门已被访问过
output = inputs[0]->getOutput();
if(func == "NOT"){
output = !output;
}else if(func == "AND"){
for (int i=1; i < inputs.size(); i++){
output &= inputs[i]->getOutput();
}
}else if(func=="OR"){
for (int i=1; i < inputs.size(); i++){
output |= inputs[i]->getOutput();
}
}else if(func=="XOR"){
for (int i=1; i < inputs.size(); i++){
output ^= inputs[i]->getOutput();
}
}else if(func=="NAND"){
for (int i=1; i < inputs.size(); i++){
output &= inputs[i]->getOutput();
}
output = !output;
}else if(func=="NOR"){
for (int i=1; i < inputs.size(); i++){
output |= inputs[i]->getOutput();
}
output = !output;
}else{
cout << "func error!!!" << endl;
}
calculated = true; //标记该门已运算过
return output;
}
}
#ifdef Log
void print(){
cout << this << " ";
cout << name << " (" << func << ") , inputs : " ;
for (int i=0; i < inputs.size(); i++){
cout << inputs[i]->name << " ";
}
cout << "" << endl;
}
#endif
};
signed main(){
int Q;// 问题数
cin>>Q;
while(Q--){
int M,N; // 输入接口数、门数
cin>>M>>N;
Gate inputs[M]; //输入设备(视为一种特殊的门)
Gate gates[N]; //门
#ifdef Log
for (int i=0; i < M; i++){
inputs[i].name = "I" + string(1 ,'1' + i);
}
for (int i=0; i < N; i++){
gates[i].name = "G" + string(1 ,'1' + i);
}
#endif
for (int i=0; i < N; i++){
cin>>gates[i].func;
int n; //该门的入度
cin>>n;
while(n--){
getchar();
char ch = getchar();
int idx;
cin>>idx;
idx--;
if(ch=='I'){
gates[i].inputs.push_back( &inputs[idx] );
}else{
gates[i].inputs.push_back( &gates[idx] );
}
}
}
#ifdef Log
for (int i=0; i < N; i++){
gates[i].print();
}
#endif
int S;
cin>>S;
bool I[S][M];// S次输入,每次输入有M个数据
for (int i=0; i < S; i++){
for (int j=0; j < M; j++){
cin>>I[i][j];
}
}
//初始化门状态
isLoop = false;
for (int i=0; i < N; i++){
gates[i].calculated = false;
gates[i].visited = false;
}
for (int i=0; i < M; i++){
inputs[i].calculated = true;
}
//把每个设备都算一下查环
for (int i=0; i < N; i++){
gates[i].getOutput();
}
for (int i=0; i < S; i++){
for (int j=0; j < M; j++){
inputs[j].output = I[i][j]; //装载输入数据到输入设备
inputs[j].calculated = true;//这样getOutput()时将直接返回output
}
for (int i=0; i < N; i++){//初始化门状态
gates[i].calculated = false;
gates[i].visited = false;
}
int n; //询问次数
cin>>n;
while(n--){
int idx;
cin>>idx;
idx--;
if(!isLoop)
cout << gates[idx].getOutput() << " ";
}
if(!isLoop){
cout << endl;
}
}
if(isLoop){
cout << "LOOP" << endl;
}
}
}