이 제출은 이전 버전의 oj.uz에서 채점하였습니다. 현재는 제출 당시와는 다른 서버에서 채점을 하기 때문에, 다시 제출하면 결과가 달라질 수도 있습니다.
#include "vision.h"
#include <vector>
using namespace std;
constexpr int bits = 9;
int n, m, k, zero, one, rowor, color, rmax, rmin, cmax, cmin;
int flatten(int x, int y)
{
return x * m + y;
}
int maxset(int begin, int ln, int startpos)
{
add_or({ begin + ln - 1 });
for (int i = 1, j = begin + ln - 2; i < ln; i++, j--)
{
add_or({ j, startpos + i - 1 });
}
for (int i = ln - 1; i >= 0; i--)
{
add_not({ startpos + i });
}
startpos += ln;
for (int i = 0; i < ln - 1; i++)
{
add_and({ startpos + i + 1, begin + i });
}
add_and({ begin + ln - 1 });
startpos += ln;
return startpos;
}
int bwnot(int begin, int ln, int startpos)
{
for (int i = 0; i < ln; i++)
{
add_not(begin + i);
}
return startpos;
}
int bwand(int begin1, int begin2, int ln, int startpos)
{
for (int i = 0; i < ln; i++)
{
add_and({ begin1 + i, begin2 + i });
}
return startpos;
}
int bwor(int begin1, int begin2, int ln, int startpos)
{
for (int i = 0; i < ln; i++)
{
add_or({ begin1 + i, begin2 + i });
}
return startpos;
}
int bwxor(int begin1, int begin2, int ln, int startpos)
{
for (int i = 0; i < ln; i++)
{
add_xor({ begin1 + i, begin2 + i });
}
return startpos;
}
int bitindex(int begin, int ln, int startpos)
{
for (int b = 0; b < bits; b++)
{
vector<int> inputs;
inputs.reserve(ln / 2);
for (int i = begin; i < begin + ln;)
{
if ((i - begin) & (1 << b))
{
inputs.push_back(i);
i++;
}
else
{
i += 1 << b;
}
}
if (inputs.empty())
{
add_xor({ 0, 0 });
}
else
{
add_or(inputs);
}
}
return startpos;
}
int gate(int begin, int ln, int condition, int startpos)
{
for (int i = 0; i < ln; i++)
{
add_and({ begin + i, condition });
}
return startpos;
}
int halfadder(int x1, int x2, int startpos)
{
add_xor({ x1, x2 });
add_and({ x1, x2 });
return startpos;
}
int fulladder(int x1, int x2, int carry, int startpos)
{
startpos = halfadder(x1, x2, startpos);
add_and({ startpos, carry });
add_xor({ startpos, carry });
add_or({ startpos + 1, startpos + 2 });
startpos += 3;
return startpos;
}
int adder(int begin1, int begin2, int startpos)
{
startpos = halfadder(begin1, begin2, startpos);
vector<int> positions;
positions.reserve(bits);
positions.push_back(startpos);
for (int i = 1; i < bits; i++)
{
startpos = fulladder(begin1 + i, begin2 + i, startpos + 1, startpos + 2);
positions.push_back(startpos);
}
startpos += 2;
for (int pos : positions)
{
add_or({ pos });
}
return startpos;
}
int increment(int begin, int startpos)
{
startpos = halfadder(begin, one, startpos);
vector<int> positions;
positions.reserve(bits);
positions.push_back(startpos);
for (int i = 1; i < bits; i++)
{
startpos = halfadder(begin + i, startpos + 1, startpos + 2);
positions.push_back(startpos);
}
startpos += 2;
for (int pos : positions)
{
add_or({ pos });
}
return startpos;
}
int negator(int begin, int startpos)
{
startpos = bwnot(begin, bits, startpos);
startpos = increment(startpos, startpos + bits);
return startpos;
}
int subtract(int begin1, int begin2, int startpos)
{
startpos = negator(begin2, startpos);
startpos = adder(startpos, begin1, startpos + bits);
return startpos;
}
int allxor(int begin, int ln, int startpos)
{
vector<int> inputs;
inputs.reserve(ln);
for (int i = 0; i < ln; i++)
{
inputs.push_back(begin + i);
}
add_xor(inputs);
return startpos;
}
int compare(int begin, int x, int startpos)
{
vector<int> inputs;
for (int i = 0; i < bits; i++)
{
if (x & (1 << i))
{
inputs.push_back(add_or({ begin + i }));
}
else
{
inputs.push_back(add_not(begin + i));
}
}
return add_and(inputs);
}
void construct_network(int N, int M, int K)
{
n = N;
m = M;
k = K;
zero = add_xor({ 0, 0 });
one = add_not(zero);
rowor = one + 1;
color = rowor + n;
for (int i = 0; i < n; i++)
{
vector<int> row;
row.reserve(m);
for (int j = 0; j < m; j++)
{
row.push_back(flatten(i, j));
}
add_or(row);
}
for (int j = 0; j < m; j++)
{
vector<int> col;
col.reserve(n);
for (int i = 0; i < n; i++)
{
col.push_back(flatten(i, j));
}
add_or(col);
}
int rmaxset = maxset(rowor, n, color + m);
int cmaxset = maxset(color, m, rmaxset + n);
int notrmaxset = bwnot(rmaxset, n, cmaxset + m);
int notcmaxset = bwnot(cmaxset, m, notrmaxset + n);
int rminset = bwand(rowor, notrmaxset, n, notcmaxset + m);
int cminset = bwand(color, notcmaxset, m, rminset + n);
int rmaxindex = bitindex(rmaxset, n, cminset + m);
int cmaxindex = bitindex(cmaxset, m, rmaxindex + bits);
int rminindex = bitindex(rminset, n, cmaxindex + bits);
int cminindex = bitindex(cminset, m, rminindex + bits);
int rdiff = subtract(rmaxindex, rminindex, cminindex + bits);
int rxor = allxor(rowor, n, rdiff + bits);
int rcond = add_not(rxor);
rdiff = gate(rdiff, bits, rcond, rcond + 1);
int cdiff = subtract(cmaxindex, cminindex, rdiff + bits);
int cxor = allxor(color, m, cdiff + bits);
int ccond = add_not(cxor);
cdiff = gate(cdiff, bits, ccond, ccond + 1);
int distance = adder(rdiff, cdiff, cdiff + bits);
compare(distance, k, distance + bits);
}
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |
# | Verdict | Execution time | Memory | Grader output |
---|
Fetching results... |