2020.7.6 热身训练赛(六)

Table of Contents

  1. 2020.7.6 热身训练赛(六)
    1. A Rush Hour Puzzle
      1. solution
      2. code
    2. H Mining a
    3. E The League of Sequence Designers
      1. solution
      2. code

2020.7.6 热身训练赛(六)

A Rush Hour Puzzle

solution

bfs.

  1. 状态用一个结构体保存;

  2. 状态判重用set;

  3. 当把结构体放入set中时,要对 “<” 进行重载。

    friend bool operator < (node p, node q) {
    
    }
    
  4. 每次移动等价于0和一个数字位置的交换。这样只用考虑0就行了。

  5. 只有一个出口。

code

#include <bits/stdc++.h>
using namespace std;
struct node {
    int mp[6][6],mov;
    friend bool operator < (node p, node q) {
        for (int i = 0; i< 6; ++i)
            for (int j = 0; j<6; ++j)
                if (p.mp[i][j] != q.mp[i][j]) return p.mp[i][j] < q.mp[i][j];
        return 0;
    }
}st;
queue<node>q;
set<node>vis;
int to[4][2] = {0,1,0,-1,1,0,-1,0};
inline bool inrg(int x,int y){
    return x>=0&&x<6&&y>=0&&y<6;
}
int main() {
    for (int i = 0; i< 6; ++i){
        for (int j = 0; j<6; ++j){
            scanf("%d", &st.mp[i][j]);
        }
    }
    st.mov = 0;
    q.push(st);
    vis.insert(st);
    while(q.size()) {
        node u = q.front(),nu;
        q.pop();
        if (u.mp[2][5] == 1) {
            int len = 1;
            for (int i = 4; i >=0; --i) {
                if (u.mp[2][i]!=1) break;
                ++len;
            }
            int ans = (u.mov + len);
            if (ans > 10) ans = -1;
            printf("%d
", ans);
            return 0;
        }
        if (u.mov == 10) break;
        for (int i = 0; i< 6; ++i) {
            for (int j = 0; j<6; ++j) {
                if (u.mp[i][j] == 0) {
                    for (int k = 0; k < 4; ++k) {
                        int x = i+to[k][0], y = j+to[k][1];
                        if((!inrg(x,y))||u.mp[x][y] == 0) continue;
                        int xx = x+to[k][0], yy = y +to[k][1];
                        if((!inrg(xx,yy))||u.mp[x][y]!=u.mp[xx][yy]) continue;
                        while(inrg(xx,yy)&&u.mp[x][y]==u.mp[xx][yy]){
                            xx = xx+to[k][0];
                            yy = yy+to[k][1];
                        }
                        xx = xx-to[k][0];
                        yy = yy-to[k][1];
                        nu = u;
                        ++nu.mov;
                        swap(nu.mp[i][j],nu.mp[xx][yy]);
                        if(!vis.count(nu)) {
                            vis.insert((nu));
                            q.push(nu);
                        }
                    }
                }
            }
        }
    }
    printf("-1
");
    return 0;

}

H Mining a

这个不会证明。

E The League of Sequence Designers

solution

构造题,假设答案序列a的长度为n,且a[1] = -1,a[i] >=0,sum a[i] = m(2<=i<=n),则按照错误方法算出来的结果为 (n-1)*m,假设按照正确方法算出来的结果为 n*(m-1) (即 n*(m-1) > (n-1)*m), 由题意可得 n*(m-1) - (n-1)*m = k. 解得 m =n + k. 也就是构造一个a[1] = -1, sum a[i] = n + k(2<=i<=n, a[i]<=1e9)的序列即可。

code

#include<cstdio>
#include<iostream>
using namespace std;
const int len = 1999;
const int Max = 1000000;
int main()
{
	int T;
	cin>>T;
	while(T--)
	{
		long long K,L;
		cin>>K>>L;
		if(L>=2000){
			puts("-1");
			continue;
		}
		printf("%d
-1",len);
		long long now= len +K;
		for(int i =1;i<len;i++)
		{
			if(now>=Max)
			{
				printf(" %d",Max);
				now-=Max;
			}
			else
			{
				printf(" %d",now);
				now=0;
			}
		}
		puts("");
	}
}
原文地址:https://www.cnblogs.com/huihao/p/13265442.html