NC231653. Liyuu的狂热粉丝的计算机
描述
in 65 56 45 mov 15 1 1 in 45 14 475 cmp 1 15 2 jz 0 4 4
(两个out之间需要空格) |
输入描述
输入的第一行包括两个整数表示有有条指令和个数据内存单元
接下来为行,每一行一段指令,表示了将要执行的程序,保证所有指令均符合格式。
接着一行给出若干(可能没有)整数,表示Liyuu的狂热粉丝给机器的输入,初号机可能不会读取到所有输入,但保证初号机总是能读到整数。
输出描述
输出一行整数(可能没有),表示Liyuu的狂热粉丝的机器的输出。
如果机器运行遇到了非法情况,则换行输出"error"。
示例1
输入:
5 5 in 1 2 3 add 1 0 15 in 1 2 3 add 15 1 15 out 12 31 41 1 1
输出:
2
示例2
输入:
6 5 in 1 2 3 add 1 0 15 in 312 45 1 add 15 1 15 add 16 1 15 out 15 145 4 1 1
输出:
error
说明:
示例3
输入:
7 10 in 1 2 3 mov 15 1 2 in 1 2 3 cmp 1 15 1 mov 14 15 1 out 1 2 3 jz 0 2 3 14 14 14 14 15 16
输出:
1 1 0
C++(g++ 7.5.0) 解法, 执行用时: 3ms, 内存消耗: 460K, 提交时间: 2022-09-07 13:55:07
#include<bits/stdc++.h> using namespace std; typedef long long ll; std::vector<std::string> split(const std::string& s, std::string c = " ") { std::vector<std::string> ret; std::size_t pos1 = 0, pos2 = s.find(c); while (pos2 != std::string::npos) { ret.emplace_back(s.substr(pos1, pos2 - pos1)); pos1 = pos2 + 1; pos2 = s.find(c, pos1); } if (pos1 != s.size()) ret.emplace_back(s.substr(pos1)); ret.erase(std::remove_if(ret.begin(), ret.end(), [&s](const std::string& rhs) -> bool { return rhs.empty(); }), ret.end()); return ret; } int f = 0; void ERR() { cout << endl; cout << "error" << endl; exit(0); } int main() { int n, m; cin >> n >> m; vector<tuple<string,int,int,int>> ops(n); for(auto &[s, a, b, c] : ops) { cin >> s >> a >> b >> c; } cin.get(); string p; getline(cin, p); vector<int> inputs; if(!p.empty()) { vector<string> ps = split(p, " "); for(auto s : ps) { inputs.push_back(stoi(s)); } } reverse(inputs.begin(), inputs.end()); vector<int> mem(m + 16); for(int i = 0; i < n;) { auto [s, a, b, c] = ops[i]; if(s == "in") { assert(!inputs.empty()); mem[15] = inputs.back(); inputs.pop_back(); } else if(s == "out") { f = 1; cout << mem[15] << " "; } else if(s == "mov") { if(b == 0 || b >= mem.size() || a >= mem.size()) ERR(); mem[b] = mem[a]; } else if(s == "add") { if(1 <= a && a <= 15 && 0 <= b && b <= 15 && 0 <= c && c <= 15) { } else { ERR(); } mem[a] = mem[b] + mem[c]; } else if(s == "cmp") { if(0 <= a && a <= 15 && 0 <= b && b <= 15) { } else { ERR(); } if(mem[a] == mem[b]) mem[14] = 1; else if(mem[a] > mem[b]) mem[14] = 2; else mem[14] = 0; } else if(s == "jz") { if(a > n) ERR(); if(mem[14] == 1) { if(a == n) break; i = a; continue; } } else if(s == "jnz") { if(a > n) ERR(); if(mem[14] != 1) { if(a == n) break; i = a; continue; } } else if(s == "jg") { if(a > n) ERR(); if(mem[14] == 2) { if(a == n) break; i = a; continue; } } else { assert(0); } ++i; } return 0; }
Python3 解法, 执行用时: 41ms, 内存消耗: 4840K, 提交时间: 2021-12-13 00:34:35
n,m = list(map(int,input().split(" "))) inst = [] for _ in range(n): tmp = input().split(" ") for i in range(1,len(tmp)): tmp[i] = int(tmp[i]) inst.append(tmp) inp = list(map(int,input().split(" "))) inp.reverse() reg = [0] * 16 mem = [0] * m outs = [] def solve(): global inp,reg,mem,outs idx = 0 getOp = lambda num: inst[idx][1:1+num] if num > 1 else inst[idx][1] ob0 = lambda v: not (0 <= v and v <= 15) ob1 = lambda v: not (1 <= v and v <= 15) while idx < n: if inst[idx][0] == "in": reg[15] = inp.pop() elif inst[idx][0] == "out": outs.append(reg[15]) elif inst[idx][0] == "mov": a,b = getOp(2) if a < 0 or b <= 0: return False try: val = reg[a] if a < 16 else mem[a-16] if b >= 16: mem[b-16] = val else: reg[b] = val except IndexError: return False elif inst[idx][0] == "add": a,b,c = getOp(3) if ob1(a) or ob0(b) or ob0(c): return False reg[a] = reg[b] + reg[c] elif inst[idx][0] == "cmp": a,b = getOp(2) if ob0(a) or ob0(b): return False reg[14] = 1 if reg[a] == reg[b] else (2 if reg[a] > reg[b] else 0) elif inst[idx][0] == "jz": a = getOp(1) if a < 0 or a > n: return False if reg[14] == 1: idx = a-1 elif inst[idx][0] == "jnz": a = getOp(1) if a < 0 or a > n: return False if reg[14] != 1: idx = a-1 elif inst[idx][0] == "jg": a = getOp(1) if a < 0 or a > n: return False if reg[14] == 2: idx = a-1 else: return False idx += 1 return True fl = solve() print(*outs) if not fl: print("error")
C++ 解法, 执行用时: 4ms, 内存消耗: 476K, 提交时间: 2021-12-12 14:04:19
#include<bits/stdc++.h> using namespace std; const int N=1e3+10; int n,m; string str[N]; int p[N][3]; int reg[N]; inline bool check_reg1(int x) { return x>0&&x<16; } inline bool check_reg0(int x) { return x>=0&&x<16; } inline bool check_mem(int x) { return x>15&&x<16+m; } inline int err() { puts(""); puts("error"); exit(0); } inline int cmp(int x,int y) { if(x==y) return 1; if(x>y) return 2; return 0; } int main() { cin>>n>>m; for(int i=0;i<n;i++) cin>>str[i]>>p[i][0]>>p[i][1]>>p[i][2]; int i=0,x; while(i<n) { if(str[i]=="in") cin>>reg[15]; else if(str[i]=="out") cout<<reg[15]<<' '; else if(str[i]=="mov"&&(check_reg1(p[i][0])||check_mem(p[i][0])) &&(check_reg1(p[i][1])||check_mem(p[i][1]))) reg[p[i][1]]=reg[p[i][0]]; else if(str[i]=="add"&&check_reg1(p[i][0])&&check_reg0(p[i][1])&&check_reg0(p[i][2])) reg[p[i][0]]=reg[p[i][1]]+reg[p[i][2]]; else if(str[i]=="cmp"&&check_reg0(p[i][0])&&check_reg0(p[i][1])) reg[14]=cmp(reg[p[i][0]],reg[p[i][1]]); else if(str[i]=="jz"&&(p[i][0]<n||(p[i][0]==n)&&i==n-1)) i=reg[14]==1?p[i][0]-1:i; else if(str[i]=="jnz"&&(p[i][0]<n||(p[i][0]==n)&&i==n-1)) i=reg[14]!=1?p[i][0]-1:i; else if(str[i]=="jg"&&(p[i][0]<n||(p[i][0]==n)&&i==n-1)) i=reg[14]==2?p[i][0]-1:i; else err(); i++; } return 0; }