【xdoj新手教学】WEEKLY MISSION 4

题目链接
给自己挖了一个天坑,终于给填上了,看了很多,写了很多,研究了很多,思考了很多,也感觉收获了很多,感觉很多对于搜索题,甚至是图论题和dp的理解都加深了。

这次的题目简介我已经写在了这周的课件中,大家可以参考,所以这里我只稍微写写关于每道题做法的一些具体细节(随便写写)。

所有代码都是手写的(有一些参考了某些前辈的经验),相比于最优的差了很多,仅供参考

前面几道基本题
A

# include <stdio.h>
# include <string.h>
# include <algorithm>
# include <vector>

using namespace std;

typedef pair<int ,int> P;

int N, M, T;
int dx[8] = {-2 , -2 , -1 , -1 , 1 , 1 , 2 , 2}, dy[8] = {-1 , 1 , -2 , 2 , -2 , 2 , -1 , 1};

bool used[26][26];
vector<P> path;
bool f;

bool dfs(P x , int n)
{
    if(f)
        return false;

    if(n == N * M)
    {
        path.push_back(x);
        f = 1;
        return true;
    }

    used[x.first][x.second] = 1;

    int i;
    for(i = 0 ; i < 8 ; i++)
    {
        int nx = x.first + dx[i], ny = x.second + dy[i];
        if(nx >= 0 && nx < N && ny >= 0 && ny < M && !used[nx][ny] && dfs(P(nx , ny) , n + 1))
        {
            path.push_back(x);
            return true;
        }
    }

    used[x.first][x.second] = 0;

    return false;
}

int main()
{
    scanf("%d", &T);

    int num = 1;
    while(T--)
    {
        path.clear();
        memset(used , 0 , sizeof(used));
        f = 0;

        scanf("%d %d", &M, &N);

        printf("Scenario #%d:\n", num++);
        if(!dfs(P(0 , 0) , 1))//其实有点冒险,因为只从0,0这个地方开始过 
            puts("impossible");
        else
        {
            reverse(path.begin() , path.end());
            int i;
            for(i = 0 ; i < path.size() ; i++)
                printf("%c%d", path[i].first + 'A', path[i].second + 1);

            puts("");
        }
        puts("");
    }

    return 0;
}

B

# include <stdio.h>
# include <queue>
# include <string.h>
# include <algorithm>

using namespace std;

typedef pair<int , int> P;

int T, N, M;
int sx, sy, ex, ey;
int dx[4] = {-1 , 0 , 1 , 0}, dy[4] = {0 , 1 , 0 , -1};
char box[40][41];
int f[40][40];

void dfs(int x , int y)
{
    f[x][y] = 1;

    int i, j;
    for(i = -1 ; i <= 1 ; i++)
    {
        for(j = - 1 ; j <= 1 ; j++)
        {
            int nx = x + i, ny = y + j;
            if(nx < N && nx >= 0 && ny < M && ny >= 0)
            {
                if(box[nx][ny] != '#')
                    f[nx][ny] = 2;
                else if(f[nx][ny] != 1)
                    dfs(nx , ny);
            }
        }
    }
}

void bfs(int x , int y)
{
    queue<P> que;

    que.push(P(x , y));
    f[x][y] = 1;

    while(!que.empty())
    {
        P r = que.front();
        que.pop();

        if(box[r.first][r.second] == 'E')
        {
            printf("%d\n", f[r.first][r.second]);
            return;
        }

        int i;
        for(i = 0 ; i < 4 ; i++)
        {
            int nx = r.first + dx[i], ny = r.second + dy[i];
            if(nx >= 0 && nx < N && ny >= 0 && ny < M && box[nx][ny] != '#' && f[nx][ny] == -1)
            {
                f[nx][ny] = f[r.first][r.second] + 1;
                que.push(P(nx , ny));
            }
        }
    }
}

int main()
{
    scanf("%d", &T);

    while(T--)
    {
        scanf("%d %d", &M, &N);

        int i, j;
        for(i = 0 ; i < N ; i++)
            scanf("%s", box[i]);

        for(i = 0 ; i < N ; i++)
        {
            for(j = 0 ; j < M ; j++)
            {
                if(box[i][j] == 'S')
                {
                    sx = i;
                    sy = j;
                }
            }
        }

        int bo;
        if(sx == 0)
            bo = 2;
        else if(sx == N - 1)
            bo = 0;
        else if(sy == 0)
            bo = 1;
        else
            bo = 3;

        memset(f , 0 , sizeof(f));
        dfs(sx + dx[(bo + 3) % 4] , sy + dy[(bo + 3) % 4]);

        int nx = sx, ny = sy, step = 1, po = bo;
        while(box[nx][ny] != 'E')
        {
            po = (po + 3) % 4;
            for(i = 0 ; i < 4 ; i++)
            {
                int mx = nx + dx[(po + i) % 4], my = ny + dy[(po + i) % 4];

                if(mx >= 0 && mx < N && my >= 0 && my < M && f[mx][my] == 2)
                {
                    nx = mx;
                    ny = my;
                    po = (po + i) % 4;
                    break;
                }
            }
            step++;
        }
        printf("%d ", step);

        memset(f , 0 , sizeof(f));
        dfs(sx + dx[(bo + 1) % 4] , sy + dy[(bo + 1) % 4]);

        nx = sx, ny = sy, step = 1, po = bo;
        while(box[nx][ny] != 'E')
        {
            po = (po + 1) % 4;
            for(i = 4 ; i >= 1 ; i--)
            {
                int mx = nx + dx[(po + i) % 4], my = ny + dy[(po + i) % 4];

                if(mx >= 0 && mx < N && my >= 0 && my < M && f[mx][my] == 2)
                {
                    nx = mx;
                    ny = my;
                    po = (po + i) % 4;
                    break;
                }
            }
            step++;
        }
        printf("%d ", step);

        memset(f , -1 , sizeof(f));
        bfs(sx , sy);
    }

    return 0;
}

C

# include <stdio.h>
# include <stack>

using namespace std;

struct com
{
    int x, y, c, step;
};

const int MAX_N = 21;
int filed[MAX_N][MAX_N];
int N, M;
int sx, sy;
int ans;

int min(int a , int b)
{
    return (a < b) ? a : b;
}

void solve()
{
    ans = 12;
    stack<com> t;

    com t11 = {sx , sy , 1 , 0};
    com t22 = {sx , sy , 2 , 0};
    com t33 = {sx , sy , 3 , 0};
    com t44 = {sx , sy , 4 , 0};
    t.push(t11);
    t.push(t22);
    t.push(t33);
    t.push(t44);

    while(!t.empty())
    {
        com ui = t.top();
        t.pop();

        if(ui.c == 5)
        {
            filed[ui.x][ui.y] = 1;
            continue;
        }

        if(ui.step == 10)
            continue;

        if(ui.c == 1)
        {
            int path;

            if((ui.x < N - 1) ? filed[ui.x + 1][ui.y] == 1 : 1)
                continue;

            for(path = ui.x ; (path < N - 2) ? filed[path + 1][ui.y] != 1 : 0 ; path++)
            {
                if(filed[path][ui.y] == 3)
                    break;
            }

            if(filed[path][ui.y] == 3)
            {
                ans = min(ans , ui.step + 1);
                continue;
            }

            if(filed[path + 1][ui.y] == 3)
            {
                ans = min(ans , ui.step + 1);
                continue;
            }

            if(filed[path + 1][ui.y] == 1)
            {
                filed[path + 1][ui.y] = 0;
                com t5 = {path + 1 , ui.y , 5 , ui.step + 1};
                com t1 = {path , ui.y , 1 , ui.step + 1};
                com t2 = {path , ui.y , 2 , ui.step + 1};
                com t3 = {path , ui.y , 3 , ui.step + 1};
                com t4 = {path , ui.y , 4 , ui.step + 1};
                t.push(t5);
                t.push(t1);
                t.push(t2);
                t.push(t3);
                t.push(t4);
            }
        }
        else if(ui.c == 2)
        {
            int path;

            if((ui.x > 0) ? filed[ui.x - 1][ui.y] == 1 : 1)
                continue;

            for(path = ui.x ; (path > 1) ? filed[path - 1][ui.y] != 1 : 0 ; path--)
            {
                if(filed[path][ui.y] == 3)
                    break;
            }

            if(filed[path][ui.y] == 3)
            {
                ans = min(ans , ui.step + 1);
                continue;
            }

            if(filed[path - 1][ui.y] == 3)
            {
                ans = min(ans , ui.step + 1);
                continue;
            }

            if(filed[path - 1][ui.y] == 1)
            {
                filed[path - 1][ui.y] = 0;
                com t5 = {path - 1 , ui.y , 5 , ui.step + 1};
                com t1 = {path , ui.y , 1 , ui.step + 1};
                com t2 = {path , ui.y , 2 , ui.step + 1};
                com t3 = {path , ui.y , 3 , ui.step + 1};
                com t4 = {path , ui.y , 4 , ui.step + 1};
                t.push(t5);
                t.push(t1);
                t.push(t2);
                t.push(t3);
                t.push(t4);
            }
        }
        else if(ui.c == 3)
        {
            int path;

            if((ui.y > 0) ? filed[ui.x][ui.y - 1] == 1 : 1)
                continue;

            for(path = ui.y ; (path > 1) ? filed[ui.x][path - 1] != 1 : 0 ; path--)
            {
                if(filed[ui.x][path] == 3)
                    break;
            }

            if(filed[ui.x][path] == 3)
            {
                ans = min(ans , ui.step + 1);
                continue;
            }

            if(filed[ui.x][path - 1] == 3)
            {
                ans = min(ans , ui.step + 1);
                continue;
            }

            if(filed[ui.x][path - 1] == 1)
            {
                filed[ui.x][path - 1] = 0;
                com t5 = {ui.x , path - 1 , 5 , ui.step + 1};
                com t1 = {ui.x , path , 1 , ui.step + 1};
                com t2 = {ui.x , path , 2 , ui.step + 1};
                com t3 = {ui.x , path , 3 , ui.step + 1};
                com t4 = {ui.x , path , 4 , ui.step + 1};
                t.push(t5);
                t.push(t1);
                t.push(t2);
                t.push(t3);
                t.push(t4);
            }
        }
        else if(ui.c == 4)
        {
            int path;

            if((ui.y < M - 1) ? filed[ui.x][ui.y + 1] == 1 : 1)
                continue;

            for(path = ui.y ; (path < M - 2) ? filed[ui.x][path + 1] != 1 : 0 ; path++)
            {
                if(filed[ui.x][path] == 3)
                    break;
            }

            if(filed[ui.x][path] == 3)
            {
                ans = min(ans , ui.step + 1);
                continue;
            }

            if(filed[ui.x][path + 1] == 3)
            {
                ans = min(ans , ui.step + 1);
                continue;
            }

            if(filed[ui.x][path + 1] == 1)
            {
                filed[ui.x][path + 1] = 0;
                com t5 = {ui.x , path + 1 , 5 , ui.step + 1};
                com t1 = {ui.x , path , 1 , ui.step + 1};
                com t2 = {ui.x , path , 2 , ui.step + 1};
                com t3 = {ui.x , path , 3 , ui.step + 1};
                com t4 = {ui.x , path , 4 , ui.step + 1};
                t.push(t5);
                t.push(t1);
                t.push(t2);
                t.push(t3);
                t.push(t4);
            }
        }

    }

    printf("%d\n", (ans == 12) ? -1 : ans);
}

int main()
{
    while(1)
    {
        scanf("%d %d", &M, &N);

        if(M == 0 && N == 0)
            break;

        int i, j;
        for(i = 0 ; i < N ; i++)
        {
            for(j = 0 ; j < M ; j++)
            {
                scanf("%d", &filed[i][j]);

                if(filed[i][j] == 2)
                {
                    sx = i;
                    sy = j;
                }
            }
        }

        solve();
    }

    return 0;
}

D

# include <stdio.h>
# include <string.h>

bool z[8];
int N, K;

char box[8][9];

int dfs(int x , int y , int num)
{   
    if(num == K)
        return 1;

    z[y] = 1;
    int i, ans = 0, j;
    for(j = 1 ; x + j < N ; j++)
    {
        for(i = 0 ; i < N ; i++)
        {
            if(box[x + j][i] == '#' && !z[i])
                ans += dfs(x + j , i , num + 1);
        }
    }

    z[y] = 0;
    return ans;
}

int main()
{
    while(1)
    {
        scanf("%d %d", &N, &K);

        if(N == -1)
            break;

        int i, j;
        for(i = 0 ; i < N ; i++)
            scanf("%s", box[i]);

        memset(z , 0 , sizeof(z));
        int ans = 0;
        for(j = 0 ; j < N ; j++)
            for(i = 0 ; i < N ; i++)
                if(box[j][i] == '#')
                    ans += dfs(j , i , 1);

        printf("%d\n", ans);
    }

    return 0;
}

E

# include <cstdio>
# include <cstring>
# include <algorithm>
# include <stack>

using namespace std;

const int MAX_N = 20;

int A[MAX_N][MAX_N];
int used[1 << MAX_N];
int N;

int ans;

int main()
{
    while(~scanf("%d", &N))
    {
        memset(used , -1 , sizeof(used));

        int i, j;
        for(i = 0 ; i < N ; i++)
            for(j = 0 ; j < N ; j++)
                scanf("%d", &A[i][j]);

        ans = 0;
        used[0] = 0;

        stack<int> s;
        s.push(0);

        while(!s.empty())
        {
            int x = s.top();
            s.pop();
            ans = max(ans , used[x]);

            for(i = 1 ; i < N ; i++)
            {
                int k = x;
                if((x >> i) & 1)
                    k -= (1 << i);
                else
                    k += (1 << i);

                if(used[k] == -1)
                {
                    used[k] = used[x];
                    int pos = ((x >> i) & 1);
                    for(j = 0 ; j < N ; j++)
                    {
                        if(pos == ((x >> j) & 1))
                            used[k] += A[i][j];
                        else
                            used[k] -= A[i][j];
                    }

                    s.push(k);
                }
            }

        }

        printf("%d\n", ans);
    }

    return 0;
}

F

# include <stdio.h>

typedef long long ll;

ll N;
bool f;

void dfs(ll k)
{
    if(f)
        return;

    if(k % N == 0)
    {
        printf("%lld\n", k);
        f = 1;
    }
    else if(k <= 1e18) 
    {
        dfs(10 * k + 1);
        dfs(10 * k);
    }
}

int main()
{
    while(1)
    {
        scanf("%lld", &N);

        if(!N)
            break;
        //for(int i = 1 ; i <= 200 ; i++)
        {
        f = 0;
        dfs(1);
        }
    }


    return 0;
}

G

# include <stdio.h>
# include <algorithm>
# include <queue>

using namespace std;

typedef long long ll;

const int INF = 100000000;
const int MAX_N = 10000;

bool pri[MAX_N];
int d[MAX_N];

int num, T, N, M;

ll tim(ll a , ll b , ll mo)
{
    a %= mo;
    b %= mo;

    ll ans = 0;

    while(b)
    {
        if(b & 1)
        {
            ans += a;
            if(ans > mo)
                ans -= mo;
        }

        b >>= 1;
        a <<= 1;
        if(a > mo)
            a -= mo;
    }

    return ans;
}

ll po(ll a , ll b , ll mo)
{
    ll ans = 1;

    while(b)
    {
        if(b & 1)
            ans = tim(ans , a , mo);

        b >>= 1;

        a = tim(a , a , mo);
    }

    return ans;
}

bool fi(ll n , ll d , ll mo , ll t)
{
    ll y = po(t , n , mo), i;

    for(i = 0 ; i < d ; i++)
    {
        ll now = tim(y , y , mo);

        if(now == 1 && y != mo - 1 && y != 1)
            return false;

        y = now;
    }

    if(y != 1)
        return false;

    return true;
}

bool MR(ll n)
{
    if(n < 2)
        return false;

    if(n == 2 || n == 3)
        return true;

    if(n & 1 == 0 || n % 3 == 0)
        return false;

    ll m = n - 1, d = 0;

    while(m & 1 == 0)
    {
        m >>= 1;
        d++;
    }

    ll t[8] = {2 , 3 , 7 , 61 , 24251 , 111 , 242 , 3537}, i;
    for(i = 0 ; i < 8 ; i++)
    {
        if(t[i] < n && !fi(m , d , n , t[i]))
            return false;
    }

    return true;
}

void bfs(int s , int g)
{
    queue<int> que;

    que.push(s);
    d[s] = 0;
    while(!que.empty())
    {
        int y = que.front();
        que.pop();

        if(y == g)
        {
            printf("%d\n", d[g]);
            return;
        }

        int dp[4] = {y / 1000 % 10 , y / 100 % 10 , y / 10 % 10 , y % 10}, i, j, k = 1000;
        for(i = 0 ; i < 4 ; i++)
        {
            for(j = 0 ; j < 10 ; j++)
            {
                if((i == 0 && j == 0) || j == dp[i])
                    continue;

                int nu = y + (j - dp[i]) * k;
                if(pri[nu] && d[nu] == INF)
                {
                    d[nu] = d[y] + 1;
                    que.push(nu);
                }
            }

            k /= 10;
        }
    }
}

void solve()
{
    fill(d , d + MAX_N , INF);

    bfs(N , M);
}

void sea()
{
    num = 0;
    int i;
    for(i = 1001 ; i <= 9997 ; i++)
    {
        if(MR(i))
        {
            pri[i] = true;
        }
    }
}

int main()
{
    sea();
    scanf("%d", &T);

    while(T--)
    {
        scanf("%d %d", &N, &M);

        solve();
    }

    return 0;
}

H

# include <cstdio>
# include <cstring>
# include <algorithm>
# include <queue>

using namespace std;

const int MAX_N = 101;

typedef pair<int , int> P;

int box[1000];
int num;

P prv[MAX_N * MAX_N];
int d[MAX_N][MAX_N];
int A , B , C;

char s[6][20] = {"DROP(1)" , "DROP(2)" ,"FILL(1)" ,"FILL(2)" , "POUR(2,1)" ,"POUR(1,2)"};

int gcd(int a , int b)
{
    if(!b)
        return a;

    return gcd(b , a % b);
}

int main()
{
    scanf("%d %d %d", &A, &B, &C);

    int i;

    if(C % gcd(A , B))
    {
        puts("impossible");
    }
    else
    {
        memset(d , -1 , sizeof(d));
        d[0][0] = 0;

        queue<int> que;
        que.push(0);

        while(!que.empty())
        {
            int now = que.front();
            int x = now / 101, y = now % 101;
            que.pop();

            if(x == C || y == C)
            {
                num = 0;
                for(i = now ; i ; i = prv[i].first)
                    box[num++] = prv[i].second;

                printf("%d\n", num);
                for(i = num - 1 ; i >= 0 ; i--)
                    puts(s[box[i]]);

                return 0;
            }

            if(x && d[0][y] == -1)
            {
                prv[y] = P(now , 0);
                d[0][y] = d[x][y] + 1;
                que.push(y);
            }

            if(y && d[x][0] == -1)
            {
                prv[x * 101] = P(now , 1);
                d[x][0] = d[x][y] + 1;
                que.push(x * 101);
            }

            if(x < A && d[A][y] == -1)
            {
                prv[A * 101 + y] = P(now , 2);
                d[A][y] = d[x][y] + 1;
                que.push(A * 101 + y);
            }

            if(y < B && d[x][B] == -1)
            {
                prv[x * 101 + B] = P(now , 3);
                d[x][B] = d[x][y] + 1;
                que.push(x * 101 + B);
            }

            int nx = min(A , x + y), ny = max(0 , y - A + x);
            if(x < A && y > 0 && d[nx][ny] == -1)
            {
                prv[101 * nx + ny] = P(now , 4);
                d[nx][ny] = d[x][y] + 1;
                que.push(nx * 101 + ny);
            }

            nx = max(0 , x - B + y), ny = min(B , x + y);
            if(y < B && x > 0 && d[nx][ny] == -1)
            {
                prv[101 * nx + ny] = P(now , 5);
                d[nx][ny] = d[x][y] + 1;
                que.push(nx * 101 + ny);
            }
        }
    }

    return 0;
} 

I

# include <stdio.h>
# include <queue>
# include <string.h>

using namespace std;

struct pos
{
    int x, y, z;
};

int L, N, M;
int d[31][31][31];
int dx[6] = {1 , -1 , 0 , 0 , 0 , 0}, dy[6] = {0 , 0 , 1 , -1 , 0 , 0}, dz[6] = {0 , 0 , 0 , 0 , 1 , -1};
char box[31][31][32];

void bfs()
{
    int i, j, k;
    for(i = 0 ; i < L ; i++)
        for(j = 0 ; j < N ; j++)
            for(k = 0 ; k < M ; k++)
                if(box[i][j][k] == 'S')
                    goto TSY;

TSY: 
    pos s = {i , j , k};

    queue<pos> que;
    que.push(s);
    d[i][j][k] = 0;

    while(!que.empty())
    {
        pos y = que.front();
        que.pop();

        if(box[y.x][y.y][y.z] == 'E')
        {
            printf("Escaped in %d minute(s).\n", d[y.x][y.y][y.z]);
            return;
        }

        int i;
        for(i = 0 ; i < 6 ; i++)
        {
            int nx = y.x + dx[i], ny = y.y + dy[i], nz = y.z + dz[i];
            if(nx >= 0 && nx < L && ny >= 0 && ny < N && nz >= 0 && nz < M && box[nx][ny][nz] != '#' && d[nx][ny][nz] == -1)
            {
                d[nx][ny][nz] = d[y.x][y.y][y.z] + 1;
                pos kt = {nx , ny , nz};
                que.push(kt);
            }
        }
    }

    puts("Trapped!");
}

int main()
{
    while(1)
    {
        scanf("%d %d %d", &L, &N, &M);

        if(!L)
            break;

        int i, j;
        for(i = 0 ; i < L ; i++)
        {
            for(j = 0 ; j < N ; j++)
                scanf("%s", box[i][j]);
        }

        memset(d , -1 , sizeof(d));
        bfs();
    }

    return 0;
}

之后是剪枝的题目

J
比较坑的一道题

# include <cstdio>
# include <cstring>
# include <algorithm>
# include <vector> 

using namespace std;

const int MAX_N = 100;

typedef vector<int> mat;

int man[MAX_N];
int shu;
int box[MAX_N];
int num;

int pp[MAX_N];
int used[MAX_N];
vector<mat> G;

inline int comp(mat &a , mat &b)
{
    if(a[0] != b[0])
        return a[0] - b[0];

    int an = a.size(), bn = b.size();
    if(an != bn)
        return  bn - an;

    return box[a[1]] - box[b[1]];
}

void dfs(int n , int res)
{   
    if(!res)
    {   
        mat prv;
        for(int u = 0 ; u <= n ; u++)
        {
            prv.push_back(pp[u]);
        }

        int k;
        if(!G.empty())
            k = comp(prv , G[0]);
        else
            k = 0;

        if(k > 0)
        {
            G.clear();
            G.push_back(prv);
        }
        else if(!k)
        {
            G.push_back(prv);
        }

        return;
    }

    if(n == 4)
        return;

    int i;
    for(i = (!n) ? num - 1 : pp[n] ; i >= 0 ; i--)
    {   
        if(res >= box[i])
        {   
            used[i]++;

            if(used[i] == 1)
                pp[0]++;

            pp[n + 1] = i;
            dfs(n + 1 , res - box[i]);

            used[i]--;
            if(used[i] == 0)
                pp[0]--;
        }
    }
}

int main()
{
    shu = num = 0;
    while(~scanf("%d", &box[num++]))
    {
        int i, j;
        while(1)
        {
            int t;
            scanf("%d", &t);

            if(!t)
                break;

            box[num++] = t;
        }
        sort(box , box + num);

        int cot = 0, qi = 0, die = 0;

        for(i = 0 ; i < num ; i++)
        {
            cot++;
            box[die++] = box[i];

            if(i == num - 1 || box[i] != box[i + 1])
            {
                if(cot > 4)
                {
                    die = qi + 5;
                    qi += 5; 
                }
                else
                    qi = die;
                cot = 0;
            }
        }

        num = die;


        while(1)
        {
            int t;
            scanf("%d", &t);

            if(!t)
                break;

            man[shu++] = t;
        }

        for(i = 0 ; i < shu ; i++)
        {
            memset(used , 0 , sizeof(used));
            G.clear();

            pp[0] = 0;
            dfs(0 , man[i]);

            printf("%d ", man[i]);

            if(G.empty())
                puts("---- none");
            else
            {               
                printf("(%d): ", G[0][0]);

                if(G.size() > 1)
                    puts("tie");
                else
                {
                    int siz = G[0].size();
                    for(j = 1 ; j < siz ; j++)
                        printf("%d%s", box[G[0][siz - j]], (j == siz - 1) ? "\n" : " ");
                }
            }
        }

        shu = num = 0;
    }

    return 0;
}

K

# include <cstdio>
# include <cstring>
# include <algorithm>

using namespace std;

const int MAX_N = 20;

int A[MAX_N];
int T, N;
bool used[MAX_N]; 
int sum;

bool dfs(int res , int n , int c)
{
    if(c == 4)
        return 1;

    if(n == N)
    {
        if(!res)
            return dfs(sum / 4 , 0 , c + 1);

        return 0;
    }

    if(used[n])
        return dfs(res , n + 1 , c);

    if(dfs(res , n + 1 , c))
        return 1;

    if(res >= A[n])
    {
        used[n] = 1;

        if(dfs(res - A[n] , n + 1 , c))
            return 1;

        used[n] = 0;
    }

    return 0;
}

int main()
{
    scanf("%d", &T);

    while(T--)
    {
        scanf("%d", &N);

        sum = 0;

        int i;
        for(i = 0 ; i < N ; i++)
        {
            scanf("%d", &A[i]);
            sum += A[i];
        }

        if(sum % 4)
        {
            puts("no");
            continue;
        }

        sort(A , A + N);

        if(A[N - 1] > sum / 4)
        {
            puts("no");
            continue;
        }

        memset(used , 0 , sizeof(used));

        if(dfs(sum / 4 , 0 , 0))
            puts("yes");
        else
            puts("no");
    }

    return 0;
} 

L

# include <cstdio>
# include <cstring>
# include <algorithm>

using namespace std;

const int MAX_N = 64;

int A[MAX_N];
int N;
int sum;
int pan;
bool used[MAX_N];

bool com(int x , int y)
{
    return x > y;
}

bool dfs(int res , int n , int c)
{
    if(c == pan)
        return 1;

    if(!res)
        return dfs(sum / pan , 0 , c + 1);

    if(n == N)
        return 0;

    int i;
    for(i = n ; i < N ; i++)
    {
        if(used[i])
            continue;

        if(!used[i] && res >= A[i])
        {
            if(i > 0 && A[i] == A[i - 1] && !used[i - 1])
                continue;

            used[i] = 1;
            if(dfs(res - A[i] , i + 1 , c))
                return 1;
            used[i] = 0;
        }

        if(n == 0)
            break;
    }

    return 0;
}

int main()
{
    while(1)
    {
        scanf("%d", &N);

        if(!N)
            break;

        sum = 0;    

        int i;
        for(i = 0 ; i < N ; i++)
        {
            scanf("%d", &A[i]);
            sum += A[i];
        }

        sort(A , A + N , com);

        for(i = A[N - 1] ; i <= 3200 ; i++)
        {
            if(sum % i)
                continue;

            memset(used , 0 , sizeof(used)); 
            pan = sum / i;
            if(dfs(i , 0 , 0))
            {
                printf("%d\n", i);
                break;
            }
        }
    }

    return 0;
}

M

# include <cstdio>
# include <vector>

using namespace std;

const int MAX_N = 20;

int goal, F, N;
int ma;
bool f;

vector<int> ans;
int s[MAX_N];
int box[MAX_N];
int num;

void dfs(int x , int sum)
{
    int i;

    if(x == N)
    {
        if(sum > ma)
        {
            ma = sum;

            f = 0;
            ans.clear();
            for(i = 0 ; i < num ; i++)
                ans.push_back(box[i]);
        }
        else if(sum == ma)
            f = 1;
    }


    int k = 10;
    for(i = x ; i < N ; i++)
    {
        int t = s[x] % k;

        if(t + sum <= goal)
        {
            box[num++] = t;
            dfs(i + 1 , sum + t);
            num--;
        }

        k *= 10;
    }
}

int main()
{
    while(~scanf("%d %d", &goal, &F))
    {
        if(goal == 0 && F == 0)
            break;

        int i = 0;
        int aim = F;
        while(aim)
        {
            s[i++] = aim;
            aim /= 10;
        }

        N = i;

        ma = 0;
        dfs(0 , 0);

        if(!ma)
            puts("error");
        else if(f)
            puts("rejected");
        else
        {
            printf("%d ", ma);
            int c = ans.size();
            for(i = 0 ; i < c ; i++)
                printf("%d%s", ans[c - 1 - i], (i == c - 1) ? "\n" : " "); 
        }
    }

    return 0;
}

N

# include <cstdio>
# include <cstring>

# define mem(mj) memset(mj , 0 , sizeof(mj))

bool h[9][10], l[9][10], qu[3][3][10];

bool used[9][9];
char ans[9][10];
char box[9][10];

int T;

bool dfs(int pos)
{
    if(pos == -1)
        return 1;

    int x = pos / 9, y = pos % 9;
    if(used[x][y])
        return dfs(pos - 1);

    int i;
    for(i = 1 ; i <= 9 ; i++)
    {
        if(!h[x][i] && !l[y][i] && !qu[x / 3][y / 3][i])
        {
            h[x][i] = l[y][i] = qu[x / 3][y / 3][i] = 1;
            ans[x][y] = i + 48;

            if(dfs(pos - 1))
                return 1;

            h[x][i] = l[y][i] = qu[x / 3][y / 3][i] = 0;
        }
    }

    return 0;
}

int main()
{
    scanf("%d", &T);

    while(T--)
    {
        mem(h);
        mem(l);
        mem(qu);
        mem(used); 

        int i, j;
        for(i = 0 ; i < 9 ; i++)
        {
            scanf("%s", box[i]);
            for(j = 0 ; j < 9 ; j++)
            {
                if(box[i][j] - 48)
                {
                    ans[i][j] = box[i][j];
                    used[i][j] = 1;
                    h[i][box[i][j] - 48] = 1;
                    l[j][box[i][j] - 48] = 1;
                    qu[i / 3][j / 3][box[i][j] - 48] = 1;
                }
            }
        }

        dfs(80);
        for(i = 0 ; i < 9 ; i++)
            puts(ans[i]);
    }

    return 0;
} 

O

# include <cstdio>
# include <cstring>
# include <vector>

using namespace std;

const int MAX_N = 26;

vector<int> G[MAX_N];
int N;

int col[MAX_N];
int ms;

bool dfs(int x)
{
    if(x == N)
        return 1;

    int i, j;
    for(i = 1 ; i <= ms ; i++)
    {
        int s = G[x].size();
        for(j = 0 ; j < s ; j++)
        {
            if(col[G[x][j]] == i)
                break;
        }

        if(j == s)
        {
            col[x] = i;
            if(dfs(x + 1))
                return 1;

            col[x] = 0;
        }
    }

    return 0;
}

int main()
{
    while(1)
    {
        scanf("%d", &N);

        if(!N)
            break;

        char s[100];

        int i, j;
        for(i = 0 ; i < N ; i++)
        {
            scanf("%s", s);
            for(j = 2 ; s[j] ; j++)
                G[i].push_back(s[j] - 'A'); 
        }

        int lb = 0, ub = 26;
        while(ub - lb > 1)
        {
            ms = (lb + ub) / 2;

            memset(col , 0 , sizeof(col));
            col[0] = 1;
            if(dfs(1))
                ub = ms;
            else
                lb = ms;
        }

        printf("%d channel%s needed.\n", ub, (ub == 1) ? "" : "s");

        for(i = 0 ; i < N ; i++)
            G[i].clear();
    }

    return 0;
}

P

# include <cstdio>
# include <cstring>
# include <vector>
# include <algorithm>
# include <queue> 

using namespace std;

typedef pair<int , int> P;
typedef pair<P , P> W;
typedef pair<int , P> O;

const int INF = 1e9;
const int MAX_N = 10;

int d[MAX_N][1 << MAX_N];
vector<W> G[MAX_N];
int N, M;

int main()
{
    while(~scanf("%d %d", &N, &M))
    {
        int i;
        int s, t, c, r, y;
        for(i = 0 ; i < M ; i++)
        {
            scanf("%d %d %d %d %d", &s, &t, &c, &r, &y);

            s--;
            t--;
            c--;

            G[s].push_back(W(P(t , c) , P(r , y)));
        }

        fill(d[0] , d[0] + MAX_N * (1 << MAX_N) , INF);
        d[0][0] = 0;

        priority_queue<O , vector<O> , greater<O> > que;
        que.push(O(0 , P(0 , 0))); 

        while(!que.empty())
        {
            int len = que.top().first;
            int x = que.top().second.first;
            int s = que.top().second.second;
            que.pop();

            if(d[x][s] < len)
                continue;

            s |= (1 << x);

            int siz = G[x].size();
            for(i = 0 ; i < siz ; i++)
            {
                int t = G[x][i].first.first, c = G[x][i].first.second, c1 = G[x][i].second.first, c2 = G[x][i].second.second;

                if((s >> c) & 1)
                    c2 = c1;

                if(d[t][s] > len + c2)
                {
                    d[t][s] = len + c2;
                    que.push(O(len + c2 , P(t , s)));
                }
            }
        }

        int ms = INF;
        for(i = 0 ; i < (1 << N) ; i++)
            ms = min(ms , d[N - 1][i]);

        if(ms == INF)
            puts("impossible");
        else
            printf("%d\n", ms);

        for(i = 0 ; i < N ; i++)
            G[i].clear();
    }

    return 0;
}

Q

# include <cstdio>
# include <cstring>
# include <algorithm>
# include <vector>
# include <queue>

using namespace std;

const int MAX_N = 110;
const int MAX_M = 10010;
const int INF = 1061109567; 

typedef pair<int , int> P;
typedef pair<int , P> W;

vector<W> G[MAX_N];
int K, N, M;
int ans;

bool used[MAX_N];
int d[MAX_N][MAX_M + 1];

int main()
{
    scanf("%d", &K);
    scanf("%d %d", &N, &M);

    int i, j;
    int t, s, l, c;
    for(i = 0 ; i < M ; i++)
    {
        scanf("%d %d %d %d", &t, &s, &l, &c);
        t--;
        s--;
        G[t].push_back(W(s , P(l , c)));
    }

    ans = INF;
    memset(d , 0x3f , sizeof(d));

    queue<int> st;
    st.push(0);

    for(i = 0 ; i <= K ; i++)
        d[0][i] = 0;

    while(!st.empty())
    {
        int x = st.front();
        st.pop();

        used[x] = 0;

        int i;
        int siz = G[x].size();
        for(i = 0 ; i < siz ; i++)
        {
            int t = (G[x][i]).first, l = ((G[x][i]).second).first, c = ((G[x][i]).second).second;

            for(j = c ; j <= K ; j++)
            {
                if(d[t][j - c] > d[x][j] + l)
                {
                    d[t][j - c] = d[x][j] + l;

                    if(!used[t])
                    {
                        used[t] = 1;
                        st.push(t);
                    }

                }
            }
        }
    }

    ans = d[N - 1][0];

    if(ans == INF)
        puts("-1");
    else
        printf("%d\n", ans);


    return 0;
} 

R

# include <cstdio>
# include <cstring>

const int MAX_N = 100;
const int MAX_K = 1e4;

char s[MAX_N + 2];
int K;

int mo[MAX_N + 1];
int len;

bool ok[5][MAX_N + 1][MAX_K];

bool dfs(int x , int res , int p)
{
    if(!ok[res][x][p])
        return 0;

    if(!res)
        return !p;

    char c;

    int i, j;
    for(i = x ; i < len - res + 1 ; i++)
    {
        c = s[i];
        for(j = (i ? 0 : 1) ; j < c - 48 ; j++)
        {
            s[i] = j + 48;
            if(dfs(i + 1 , res - 1 , (p + K + (j - c + 48) * mo[len - 1 - i] % K) % K))
                return 1;
            s[i] = c;
        }
    }

    for(i = len - res ; i >= x ; i--)
    {
        c = s[i];
        for(j = c - 48 + 1 ; j < 10 ; j++)
        {
            s[i] = j + 48;
            if(dfs(i + 1 , res - 1 , (p + K + (j - c + 48) * mo[len - 1 - i] % K) % K))
                return 1;
            s[i] = c;
        }
    }

    return ok[res][x][p] = 0;
}

int main()
{
    while(~scanf("%s", s))
    {
        scanf("%d", &K);

        len = strlen(s);

        int i, j;
        int ned = 0;
        mo[0] = (K == 1) ? 0 : 1;
        for(i = 0 ; i < len ; i++)
        {
            ned = (10 * ned + s[i] - 48) % K;

            if(i > 0)
                mo[i] = mo[i - 1] * 10 % K;
        }

        memset(ok , 1 , sizeof(ok));

        for(i = 0 ; i <= 4 ; i++)
        {
            if(dfs(0 , i , ned))
            {
                puts(s);
                break;
            }
        }
    }

    return 0;
}

S

# include <cstdio>
# include <cstring>
# include <algorithm>
# include <queue>
# include <set>

using namespace std;

const int MAX_N = 16;
const int INF = 1000;

typedef pair<int , int> P;

P edg[1000];
int head[2][MAX_N];
int ed;

int cz[21];
int col[MAX_N];
int num;

int X1[MAX_N], Y1[MAX_N], X2[MAX_N], Y2[MAX_N];
int N, T;

bool used[1 << MAX_N];
int d[1 << MAX_N];

inline void add(int f , int from , int to)
{
    edg[ed].first = to;
    edg[ed].second = head[f][from];
    head[f][from] = ed++;
}

int main()
{
    scanf("%d", &T);

    while(T--)
    {
        scanf("%d", &N);

        int i, j, k;
        int c;
        set<int> s;
        num = 0;
        for(i = 0 ; i < N ; i++)
        {
            scanf("%d %d %d %d %d", &Y1[i], &X1[i], &Y2[i], &X2[i], &c);

            if(s.find(c) == s.end())
            {
                cz[c] = num++;
                s.insert(c);
            }
            col[i] = cz[c];
        }

        memset(head , 0 , sizeof(head));
        //memset(used , 0 , sizeof(used));

        ed = 1;
        for(i = 0 ; i < N ; i++)
        {
            for(j = 0 ; j < N ; j++)
            {
                if(Y2[i] == Y1[j] && X1[i] < X2[j] && X1[j] < X2[i])
                {
                    add(0 , i , j);
                    add(1 , j , i);
                }
            }
        }

        queue<int> que;
        que.push(0);
        memset(d , 0x3f , sizeof(d));
        d[0] = 0;

        while(!que.empty())
        {
            int x = que.front();
            que.pop();

            used[x] = 0;
            for(i = 0 ; i < num ; i++)
            {
                int z = x;
                bool f = 1;

                while(f)
                {
                    f = 0;

                    for(j = 0 ; j < N ; j++)
                    {
                        if((z >> j) & 1)
                            continue;

                        if(col[j] != i)
                            continue;

                        for(k = head[1][j] ; k ; k = edg[k].second)
                        {
                            if(!((z >> edg[k].first) & 1))
                                break;
                        }

                        if(!k)
                        {
                            f = 1;
                            z |= (1 << j);
                        }
                    }
                }

                if(d[z] > d[x] + 1)
                {
                    d[z] = d[x] + 1;
                    if(!used[z])
                    {
                        used[z] = 1;
                        que.push(z);
                    }
                }
            }
        }

        printf("%d\n", d[(1 << N) - 1]);
    }

    return 0;
}

T

# include <cstdio>
# include <cstring>
# include <queue>

using namespace std;

const int MAX_N = 1e6;

int d[6 * MAX_N];
int wat, now;
int ha[7] = {1 , 10 , 100 , 1000 , 10000 , 100000 , 1000000};

int main()
{
    scanf("%d %d", &now, &wat);

    memset(d , -1 , sizeof(d));

    now += 5 * ha[6];
    d[now] = 0;
    queue<int> que;
    que.push(now);

    while(!que.empty())
    {
        int x = que.front();
        que.pop();

        if(x % ha[6] == wat)
        {
            printf("%d\n", d[x]);
            return 0;
        }

        int pos = x / ha[6];

        int be = x;
        int x0 = x % ha[1];
        int xp = x / ha[pos] % ha[1];
        be += (xp - x0) + (x0 - xp) * ha[pos];
        if(d[be] == -1)
        {
            d[be] = d[x] + 1;
            que.push(be);
        }

        be = x;
        int x5 = x / ha[5] % ha[1];
        be += (xp - x5) * ha[5] + (x5 - xp) * ha[pos];
        if(d[be] == -1)
        {
            d[be] = d[x] + 1;
            que.push(be);
        }

        be = x + ha[pos];
        if(xp < 9 && d[be] == -1)
        {
            d[be] = d[x] + 1;
            que.push(be);
        }

        be = x - ha[pos];
        if(xp > 0 && d[be] == -1)
        {
            d[be] = d[x] + 1;
            que.push(be);
        }

        be = x + ha[6];
        if(pos < 5 && d[be] == -1)
        {
            d[be] = d[x] + 1;
            que.push(be);
        }

        be = x - ha[6];
        if(pos > 0 && d[be] == -1)
        {
            d[be] = d[x] + 1;
            que.push(be);
        }
    }

    return 0;
} 

U

# include <cstdio>
# include <cstring>
# include <queue>

using namespace std;

const int MAX_N = 20;
const int MAX_M = 100;
const int INF = 1061109567;

bool used[1 << MAX_N];
int d[1 << MAX_N];

int t[MAX_M];
char s[MAX_N + 1];
char st[MAX_N + 1];
int ha[2][1 << MAX_N];
int he[2][1 << MAX_N];
int N, M;

int main()
{
    int tt = 1;
    while(1)
    {
        scanf("%d %d", &N, &M);
        if(!N && !M)
            break;

        int i, j;
        for(i = 0 ; i < M ; i++)
        {
            scanf("%d %s %s", &t[i], st, s);

            int h0 = (1 << N) - 1, h1 = 0;
            int h3 = 0, h2 = (1 << N) - 1;
            for(j = 0 ; s[j] ; j++)
            {
                if(s[j] == '-')
                    h1 |= (1 << j);
                else if(s[j] == '+')
                    h0 &= ~(1 << j);

                if(st[j] == '-')
                    h2 &= ~(1 << j);
                else if(st[j] == '+')
                    h3 |= (1 << j);
            }

            ha[0][i] = h0;
            ha[1][i] = h1;
            he[0][i] = h2;
            he[1][i] = h3;
        }

        queue<int> que;
        que.push(0);

        memset(used , 0 , sizeof(used));
        memset(d , 0x3f , sizeof(d));

        d[0] = 0;

        while(!que.empty())
        {
            int x = que.front();
            que.pop();

            used[x] = 0;

            for(i = 0 ; i < M ; i++)
            {
                if(((x | he[0][i]) != (1 << N) - 1) || (x & he[1][i]))
                    continue;

                int z = x;
                z &= ha[0][i];
                z |= ha[1][i];

                if(d[z] > d[x] + t[i])
                {
                    d[z] = d[x] + t[i];
                    if(!used[z])
                    {
                        used[z] = 1;
                        que.push(z);
                    }
                }
            }
        }
        printf("Product %d\n", tt++);

        if(d[(1 << N) - 1] == INF)
            puts("Bugs cannot be fixed.");
        else
            printf("Fastest sequence takes %d seconds.\n", d[(1 << N) - 1]);

        puts("");
    }

    return 0;
}

V

# include <cstdio>
# include <cstring>
# include <algorithm>
# include <queue> 

using namespace std;

const int MAX_N = 20;
const int MAX_L = 8;

typedef pair<int , int> P;

int dx[4] = {1 , 0 , -1 , 0}, dy[4] = {0 , 1 , 0 , -1};

int d[MAX_N][MAX_N][1 << (2 * MAX_L - 2)];

int N, M, L, K;
int X[MAX_L], Y[MAX_L];

bool maz[MAX_N][MAX_N];

int dfs(int x)
{
    if(x == L - 1)
        return 0;

    int i;
    for(i = 0 ; i < 4 ; i++)
    {
        int nx = X[x] + dx[i], ny = Y[x] + dy[i];
        if(nx == X[x + 1] && ny == Y[x + 1])
            return (dfs(x + 1) << 2) + i;
    }
}

int main()
{
    int tt = 1;
    while(1)
    {
        scanf("%d %d %d", &N, &M, &L);

        if(!N && !M && !L)
            break;

        memset(d , -1 , sizeof(d));
        memset(maz , 0 , sizeof(maz));

        int i;
        for(i = 0 ; i < L ; i++)
        {
            scanf("%d %d", &X[i], &Y[i]);
            X[i]--;
            Y[i]--;
        }

        int z = dfs(0);

        scanf("%d", &K);
        for(i = 0 ; i < K ; i++)
        {
            int t, s;
            scanf("%d %d", &t, &s);
            t--;
            s--;
            maz[t][s] = 1;
        }

        queue<P> que;
        que.push(P(X[0] * M + Y[0] , z));
        d[X[0]][Y[0]][z] = 0;
        bool f = 1;

        while(!que.empty())
        {
            int x = que.front().first / M, y = que.front().first % M;
            int zh = que.front().second;
            que.pop();

            if(x == 0 && y == 0)
            {
                f = 0;
                printf("Case %d: %d\n", tt++, d[x][y][zh]);
                break;
            }

            int lx = x, ly = y, lz = zh;
            for(i = 0 ; i < L - 1 ; i++)
            {
                maz[lx][ly] = 1;
                lx += dx[lz & 3];
                ly += dy[lz & 3];
                lz >>= 2; 
            }
            maz[lx][ly] = 1;

            for(i = 0 ; i < 4 ; i++)
            {
                int nx = x + dx[i], ny = y + dy[i];
                if(nx >= 0 && nx < N && ny >= 0 && ny < M && !maz[nx][ny])
                {
                    int nz = (((zh << 2) + ((i + 2) & 3)) & ((1 << (2 * (L - 1))) - 1));
                    if(d[nx][ny][nz] == -1)
                    {
                        d[nx][ny][nz] = d[x][y][zh] + 1;
                        que.push(P(nx * M + ny , nz));
                    } 
                }
            }

            lx = x, ly = y, lz = zh;
            for(i = 0 ; i < L - 1 ; i++)
            {
                maz[lx][ly] = 0;
                lx += dx[lz & 3];
                ly += dy[lz & 3];
                lz >>= 2; 
            }
            maz[lx][ly] = 0;

        }

        if(f)
        {
            printf("Case %d: -1\n", tt++);
        }
    }

    return 0;
}

W

# include <cstdio>
# include <cstring>
# include <queue>

using namespace std;

const int MAX_N = 1e6 + 7;
const int FULL = 5e5;

struct node
{
    char box[32], pos[32];
    int d;
    int next;
};

char b[32];
node edg[FULL];
int head[MAX_N];

int ed;

int T;

bool cmp(char * s , char * t)
{
    int i;
    for(i = 0 ; i < 32 ; i++)
    {
        if(s[i] != t[i] && !(s[i] % 8 == 0 && t[i] % 8 == 0))
            return 1;
    }

    return 0;
}

int HS(char * s)
{
    unsigned int p = 0;

    int i;
    for(i = 0 ; i < 32 ; i++)
        p = p * 7 + s[i];

    return p % MAX_N;
}

bool fin(char * s)
{
    int h = HS(s);

    int i;
    for(i = head[h] ; i ; i = edg[i].next)
    {
        if(!cmp(s , edg[i].box))
            return 1;
    }

    return 0;
}

void inser(int i)
{
    int h = HS(edg[i].box);
    edg[i].next = head[h];
    head[h] = i;
}

int cp(char * s , char * t)
{
    for(int i = 0 ; i < 32 ; i++)
        s[i] = t[i];
}

void get(char &a)
{
    char ch = getchar();

    while(!(ch >= '0' && ch <= '9')) 
        ch = getchar();

    for(a = 0 ; (ch >= '0' && ch <= '9') ; ch = getchar()) 
        a = a * 10 + ch - '0';
}

void solve()
{
    memset(head , 0 , sizeof(head));
    ed = 1;

    int gai[4];//坐标  

    int i;
    for(i = 0 ; i < 32 ; i++)
    {
        if(i % 8 == 0)
            continue;

        get(edg[ed].box[i]);
        edg[ed].box[i] -= 10;
        edg[ed].box[i] = (edg[ed].box[i] / 10) * 8 + edg[ed].box[i] % 10;

        edg[ed].pos[edg[ed].box[i]] = i;

        if(edg[ed].box[i] % 8 == 1)
            gai[edg[ed].box[i] / 8] = i;
    }

    for(i = 0 ; i < 4 ; i++)
    {
        edg[ed].box[8 * i] = 8 * i + 1;
        edg[ed].box[gai[i]] = 8 * i;

        edg[ed].pos[8 * i + 1] = 8 * i;
        edg[ed].pos[8 * i] = gai[i];
    }

    if(!cmp(edg[ed].box , b))
    {
        puts("0");
        return;
    }

    edg[ed].d = 0;
    inser(ed);

    queue<int> que;
    que.push(ed++);

    while(!que.empty())
    {   
        int q = que.front();
        que.pop();

        for(i = 0 ; i < 4 ; i++)
        {
            cp(edg[ed].box , edg[q].box);
            cp(edg[ed].pos , edg[q].pos);

            int x = edg[ed].pos[8 * i] / 8, y = edg[ed].pos[8 * i] % 8;

            int am = edg[q].box[x * 8 + y - 1];
            if(am % 8 && am % 8 != 7)
            {
                int ax = edg[q].pos[am + 1] / 8, ay = edg[q].pos[am + 1] % 8;

                edg[ed].box[x * 8 + y] = am + 1;
                edg[ed].box[ax * 8 + ay] = 8 * i;
                edg[ed].pos[am + 1] = x * 8 + y;
                edg[ed].pos[8 * i] = ax * 8 + ay;

                if(!fin(edg[ed].box))
                {
                    if(!cmp(b , edg[ed].box))
                    {                       
                        printf("%d\n", edg[q].d + 1);
                        return;
                    }

                    edg[ed].d = edg[q].d + 1;
                    inser(ed);
                    que.push(ed++);
                }
            }
        }
    }
    puts("-1");
}

int main()
{
    int i, j;
    for(i = 0 ; i < 4 ; i++)
    {
        for(j = 0 ; j < 7 ; j++)
            b[i * 8 + j] = i * 8 + j + 1;

        b[i * 8 + 7] = i * 8;
    }

    scanf("%d", &T);

    while(T--)
    {
        solve();
    }

    return 0;
}

X
有很多打表的细节

# include <cstdio>
# include <cstring>
# include <algorithm>
# include <vector>
# include <queue>

using namespace std;
//w0, r1, b2, kong3
//shang 0, qian 1, you2

typedef pair<int , int> P;

const int MAX_Z = 15116544;

int e6[10];

int siz[9] = {2 , 3 , 2 , 3 , 4 , 3 , 2 , 3 , 2};
int mov[9][4][2] = {{{1 , 1} , {3 , 0}} , {{0 , 1} , {2 , 1} , {4 , 0}} , {{1 , 1} , {5 , 0}} , {{0 , 0} , {4 , 1} , {6 , 0}} , {{1 , 0} , {3 , 1} , {5 , 1} , {7 , 0}} , {{2 , 0} , {4 , 1} , {8 , 0}} , {{3 , 0} , {7 , 1}} , {{4 , 0} , {6 , 1} , {8 , 1}} , {{7 , 1} , {5 , 0}}};

int zz[6][2] = {{4 , 2} , {3 , 5} , {5 , 0} , {1 , 4} , {0 , 3} , {2 , 1}};
int col[6][3] = {{0 , 1 , 2} , {0 , 2 , 1} , {2 , 1 , 0} , {2 , 0 , 1} , {1 , 0 , 2} , {1 , 2 , 0}};

int maz[9];
int X, Y;

int num;
//9 * 6^8
char d[MAX_Z];
char d2[MAX_Z];

int main()
{   
    int i;
    e6[0] = 1;
    for(i = 0 ; i < 9 ; i++)
        e6[i + 1] = 6 * e6[i];


    while(1)
    {
        scanf("%d %d", &X, &Y);

        if(!X && !Y)
            break;
        X--;
        Y--;
        char c;
        int i, j;
        int iz[9];
        int pe;
        int qid = (Y * 3 + X) * e6[8];
        for(i = 0 ; i < 9 ; i++)
        {
            c = getchar();
            while(c < 'A' || c > 'Z')
                c = getchar();

            if(c != 'E')
            {
                if(c == 'W')
                    iz[i] = 0;
                else if(c == 'R')
                    iz[i] = 2;
                else if(c == 'B')
                    iz[i] = 1;
            }
            else
                pe = i;
        }

        memset(d , -1 , sizeof(d));
        queue<int> que;
        for(i = 0 ; i < 256 ; i++)
        {
            int Nz = i;
            int hh = 0;
            for(j = 0 ; j < 9 ; j++)
            {
                if(j == pe)
                    continue;

                hh = 6 * hh + 2 * iz[j] + (Nz & 1);
                Nz >>= 1;
            }

            hh += pe * e6[8];
            d[hh] = 0;
            que.push(hh);
        }
        //puts("haha");
        //printf("%d\n", que.size());
        while(!que.empty())
        {
            int np = que.front();
            que.pop();

            if(d[np] == 11)
                continue;

            if(np == qid)
                break;

            int zt[9];
            int e = np / e6[8];
            int nz = np % e6[8];
            for(i = 8 ; i >= 0 ; i--)
            {
                if(i == e)
                    continue;

                zt[i] = nz % 6;
                nz /= 6;
            }
            //for(i = 0 ; i < 8 ; i++)
                //printf("%d ", zt[i]);
            //printf("%d\n", e);

            for(i = 0 ; i < siz[e] ; i++)
            {
                int to = mov[e][i][0];
                int way = mov[e][i][1];

                int nw = 0;
                for(j = 0 ; j < 9 ; j++)
                {
                    if(j == e)
                        nw = 6 * nw + zz[zt[to]][way];
                    else if(j != to)
                    {
                        nw = 6 * nw + zt[j];
                    }
                }

                nw += to * e6[8];
                if(d[nw] == -1)
                {
                    d[nw] = d[np] + 1;
                    que.push(nw);
                }
            }
        }

        queue<int> q;
        int ans = 40;
        q.push(qid);
        memset(d2 , -1 , sizeof(d2));
        d2[qid] = 0;

        while(!q.empty())
        {
            int np = q.front();
            char stp = d2[np];
            q.pop();

            if(d[np] != -1)
                ans = min(stp + d[np] , ans);

            if(stp == 19)
                continue;

            int zt[9];
            int e = np / e6[8];
            int nz = np % e6[8];
            for(i = 8 ; i >= 0 ; i--)
            {
                if(i == e)
                    continue;

                zt[i] = nz % 6;
                nz /= 6;
            }

            for(i = 0 ; i < siz[e] ; i++)
            {
                int to = mov[e][i][0];
                int way = mov[e][i][1];

                int nw = 0;
                for(j = 0 ; j < 9 ; j++)
                {
                    if(j == e)
                        nw = 6 * nw + zz[zt[to]][way];
                    else if(j != to)
                        nw = 6 * nw + zt[j];
                }

                nw += e6[8] * to;

                if(d2[nw] == -1)
                {
                    d2[nw] = stp + 1;
                    q.push(nw);
                }
            }
        }

        if(ans != 40)
            printf("%d\n", ans);
        else
            puts("-1");
    }

    return 0;
}

Y

# include <iostream>
# include <cstdio> 
# include <cstring>
# include <algorithm>
# include <queue>

using namespace std;

const int MAX_E = 5e5;
const int MAX_V = 2e4 + 100;
const int INF = 2e9;

struct path
{
    int s, t, r, cry, next;
};

path edge[MAX_E];
int N, M, sos, sink, edg, mf;
int head[MAX_V], dis[MAX_V];

void addedge(int x ,int y ,int c ,int flag)
{
    edge[edg].s = x;
    edge[edg].t = y;
    edge[edg].r = c;
    edge[edg].cry = edg + 1;
    edge[edg].next = head[x];
    head[x] = edg++;
    edge[edg].s = y;
    edge[edg].t = x;
    edge[edg].cry = edg - 1;
    edge[edg].r = (flag ? c : 0);
    edge[edg].next = head[y];
    head[y] = edg++;
}

int bfs()
{
    int i, v, tmp;
    queue <int> q;

    memset(dis , 0 , sizeof(dis));
    dis[sos] = 1;
    q.push(sos);

    while(!q.empty())
    {
        v = q.front();
        q.pop();

        for(i = head[v] ; i != -1 ; i = edge[i].next)
        {
            tmp = edge[i].t;
            if(!dis[tmp] && edge[i].r)
            {
                dis[tmp] = dis[v] + 1;
                if(tmp == sink) 
                    return 1;

                q.push(tmp);
            }
        }
    }

    return 0;
}

int dfs(int cur , int cp)
{
    if(cur == sink) 
        return cp;

    int tmp = 0 , i , a , t;
    for(i = head[cur] ; i !=-1 && tmp < cp ; i = edge[i].next)
    {
        a = edge[i].t;
        if(dis[a] == dis[cur] + 1 && edge[i].r)
        {
            t = dfs(a , min(edge[i].r , cp - tmp));
            edge[i].r -= t;
            edge[edge[i].cry].r += t;
            tmp += t;
        }
    } 
    if(!tmp) 
        dis[cur] = -1;

    return tmp;
}

void dinic()
{
    mf = 0;
    while(bfs()) 
        mf += dfs(sos , INF);
}

int main()
{
    int i, a, b, c;
    while(~scanf("%d %d", &N, &M))
    {
        sos = 0;
        sink = N + 1;
        edg = 0;

        memset(head , -1 , sizeof(head));

        for(i = 1 ; i <= N ; i++)
        {
            scanf("%d %d",&a,&b);
            addedge(sos , i , a , 0);
            addedge(i , sink , b , 0);
        }
        for(i = 0 ; i < M ; i++)
        {
            scanf("%d %d %d", &a, &b, &c);
            addedge(a , b , c , 1); 
        }

        dinic();

        printf("%d\n", mf);
    }
    return 0;
}

猜你喜欢

转载自blog.csdn.net/qq_40772738/article/details/80538664