Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- #include <bits/stdc++.h>
- #include <unistd.h>
- #include <glpk.h>
- #ifdef __CYGWIN__
- #define cimg_OS 2
- #define _fileno fileno
- #define _getpid getpid
- #define _vsnprintf vsnprintf
- #define _snprintf snprintf
- #endif
- #include <CImg.h>
- using namespace cimg_library;
- using namespace std;
- #define FORE(it,c) for(__typeof((c).begin()) it = (c).begin(); it != (c).end(); ++it)
- #define FOR(i,a,b) for(int i=(a);i<(b);++i)
- #define REP(i,a) FOR(i,0,a)
- #define ZERO(m) memset(m,0,sizeof(m))
- #define ALL(x) x.begin(),x.end()
- #define PB push_back
- #define S size()
- #define LL long long
- #define ULL unsigned long long
- #define LD long double
- #define MP make_pair
- #define X first
- #define Y second
- #define VC vector
- #define PII pair <int, int>
- #define VI VC < int >
- #define VVI VC < VI >
- #define VD VC < double >
- #define VVD VC < VD >
- #define VS VC < string >
- #define DB(a) cerr << #a << ": " << (a) << endl;
- template<class T> void print(VC < T > v) {cerr << "[";if (v.S) cerr << v[0];FOR(i, 1, v.S) cerr << ", " << v[i];cerr << "]\n";}
- template<class T> string i2s(T x) {ostringstream o; o << x; return o.str(); }
- VS splt(string s, char c = ' ') {VS all; int p = 0, np; while (np = s.find(c, p), np >= 0) {if (np != p) all.PB(s.substr(p, np - p)); p = np + 1;} if (p < s.S) all.PB(s.substr(p)); return all;}
- int R, C;
- int shapes;
- int data[64][64];
- int shape[64][64];
- int tmp[64][64];
- int res[64][64];
- glp_prob *lp;
- bool ok(int r, int c) {
- return r >= 0 && r < R && c >= 0 && c < C && data[r][c];
- }
- VS solve() {
- VI lpr, lpc;
- VD lpv;
- VS pos;
- lpr.PB(0);
- lpc.PB(0);
- lpv.PB(0);
- int rows = 0;
- REP(r, R) REP(c, C) rows += data[r][c];
- REP(rot, 4) {
- memcpy(tmp, shape, sizeof(shape));
- REP(i, 64) REP(j, 64)
- shape[j][63-i] = tmp[i][j];
- FOR(offr, -64, 64) FOR(offc, -64, 64) {
- string s = "";
- REP(r, 64) REP(c, 64) if (shape[r][c] && !ok(r + offr, c + offc)) goto next;
- ZERO(tmp);
- REP(r, 64) REP(c, 64) if (shape[r][c]) {
- tmp[r + offr][c + offc] = 1;
- lpr.PB((r + offr) * 64 + (c + offc) + 1);
- lpc.PB(pos.S + 1);
- lpv.PB(1.0);
- }
- REP(r, 64) REP(c, 64) s += tmp[r][c] ? '1' : '0';
- pos.PB(s);
- next: ;
- }
- }
- glp_term_out(GLP_OFF);
- lp = glp_create_prob();
- glp_set_prob_name(lp, "sample");
- glp_set_obj_dir(lp, GLP_MAX);
- glp_add_rows(lp, 64 * 64);
- REP(r, 64) REP(c, 64) glp_set_row_bnds(lp, r * 64 + c + 1, GLP_DB, 0.0, 1.0);
- glp_add_cols(lp, pos.S);
- REP(i, pos.S) {
- glp_set_col_bnds(lp, i + 1, GLP_DB, 0.0, 1.0);
- glp_set_obj_coef(lp, i + 1, 1.0);
- glp_set_col_kind(lp, i + 1, GLP_BV);
- }
- glp_load_matrix(lp, lpr.S - 1, &lpr[0], &lpc[0], &lpv[0]);
- glp_iocp parm;
- glp_init_iocp(&parm);
- parm.presolve = GLP_ON;
- parm.cb_func = NULL;
- parm.cb_info = NULL;
- glp_intopt(lp, &parm);
- int no = glp_mip_obj_val(lp);
- cout << "Shapes Found: " << no << endl;
- VS rv;
- REP(i, pos.S) if (glp_mip_col_val(lp, i + 1)) rv.PB(pos[i]);
- glp_delete_prob(lp);
- return rv;
- }
- void calcres(VS v) {
- ZERO(res);
- REP(i, v.S) REP(r, 64) REP(c, 64) if (v[i][r * 64 + c] == '1') res[r][c] = 1 + i;
- }
- void output() {
- REP(r, R) {
- REP(c, C) {
- char cc = ' ';
- if (data[r][c]) cc = '#';
- if (res[r][c] >= 1 && res[r][c] <= 26) cc = 'A' + res[r][c] - 1;
- if (res[r][c] >= 27) cc = 'a' + res[r][c] - 27;
- cout << cc;
- }
- cout << endl;
- }
- }
- CImg < unsigned char > img;
- CImgDisplay disp;
- const int CELL_SIZE = 20;
- const int MARGIN = 2;
- unsigned char white[] = {255, 255, 255};
- unsigned char grey[] = {192, 192, 192};
- unsigned char red[] = {255, 128, 64};
- unsigned char green[] = {128, 255, 128};
- void draw() {
- img = (unsigned char)0;
- bool selectingShape = true;
- REP(r, 64) REP(c, 64) selectingShape &= res[r][c] == 0;
- REP(r, R) REP(c, C)
- if (data[r][c]) img.draw_rectangle(c * CELL_SIZE + MARGIN, r * CELL_SIZE + MARGIN, (c + 1) * CELL_SIZE - MARGIN, (r + 1) * CELL_SIZE - MARGIN, res[r][c] ? white : selectingShape && shape[r][c] ? green : grey);
- REP(r, R) REP(c, C) if (res[r][c]) {
- if (r == 0 || res[r-1][c] != res[r][c]) img.draw_rectangle(c * CELL_SIZE - 1, r * CELL_SIZE - 1, (c + 1) * CELL_SIZE + 1, r * CELL_SIZE + 1, red);
- if (r == R - 1 || res[r+1][c] != res[r][c]) img.draw_rectangle(c * CELL_SIZE - 1, (r + 1) * CELL_SIZE - 1, (c + 1) * CELL_SIZE + 1, (r + 1) * CELL_SIZE + 1, red);
- if (c == 0 || res[r][c-1] != res[r][c]) img.draw_rectangle(c * CELL_SIZE - 1, r * CELL_SIZE - 1, c * CELL_SIZE + 1, (r + 1) * CELL_SIZE + 1, red);
- if (c == C - 1 || res[r][c+1] != res[r][c]) img.draw_rectangle((c + 1) * CELL_SIZE - 1, r * CELL_SIZE - 1, (c + 1) * CELL_SIZE + 1, (r + 1) * CELL_SIZE + 1, red);
- }
- }
- int main(int argc, char **argv) {
- assert(argc > 1);
- int fileNo = atoi(argv[1]);
- int testNo = argc > 2 ? atoi(argv[2]) : 0;
- string fn = "unity" + i2s(fileNo / 10) + i2s(fileNo % 10) + ".in";
- ifstream fs(fn.c_str());
- int tc;
- fs >> tc;
- while (true) {
- fs >> shapes >> R >> C;
- REP(i, R) {
- string s;
- fs >> s;
- REP(j, C) data[i][j] = s[j] == '#';
- }
- if (testNo-- == 0) break;
- }
- fs.close();
- img = CImg<unsigned char>(C * CELL_SIZE, R * CELL_SIZE, 1, 3);
- int x = 0;
- REP(r, R) REP(c, C) x += data[r][c];
- cout << "Number of Shapes: " << shapes << endl;
- cout << "Size of Shapes: " << (x / shapes) << endl;
- ZERO(shape);
- int mouseButtons = 0;
- int lastR = 0, lastC = 0;
- while (true) {
- draw();
- disp.display(img);
- disp.wait();
- if (disp.is_keyQ()) break;
- if (disp.is_keyN()) ZERO(res);
- if (disp.is_keyC()) ZERO(res), ZERO(shape);
- if (disp.is_keyR()) {
- VS rv = solve();
- calcres(rv);
- output();
- }
- int r = disp.mouse_y() / CELL_SIZE;
- int c = disp.mouse_x() / CELL_SIZE;
- if ((disp.button() & 1) && ((mouseButtons & 1) == 0 || lastR != r || lastC != c)) {
- if (data[r][c]) shape[r][c] = 1 - shape[r][c];
- }
- mouseButtons = disp.button();
- lastR = r;
- lastC = c;
- }
- return 0;
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement