二货小易有一个W*H的网格盒子,网格的行编号为0~H-1,网格的列编号为0~W-1。每个格子至多可以放一块蛋糕,任意两块蛋糕的欧几里得距离不能等于2。
对于两个格子坐标(x1,y1),(x2,y2)的欧几里得距离为:
( (x1-x2) * (x1-x2) + (y1-y2) * (y1-y2) ) 的算术平方根
小易想知道最多可以放多少块蛋糕在网格盒子里。
每组数组包含网格长宽W,H,用空格分割.(1 ≤ W、H ≤ 1000)
输出一个最多可以放的蛋糕数
3 2
4
//把所有的行和列排成一行(与原来等价) 那么问题就变成了将蛋糕每隔一个空放一个 可以多少 import java.util.*; public class PutCakeNum{ public static int deal(int r, int c){ int n=0; if(r%4==0||c%4==0){n=r*c/2;}//如果能整除4 那么蛋糕个数为网格个数的一半 else{ n=r*c/2+1;}//不能被4整除 将蛋糕每隔一个空放一个 可以放多少 奇数的一半+1 return n; } public static void main(String args[]){ Scanner sc=new Scanner(System.in); while(sc.hasNext()){ int r=sc.nextInt(); int c=sc.nextInt(); int res=deal(r,c); System.out.println(res); } } }
//这个题画图可以知道,其实是循环的,每四行四列循环一次,因此整个盒子被分成四块区域, //分别计算四块区域即可 import java.util.Scanner; public class Main{ public static void main(String[] args){ Scanner sc = new Scanner(System.in); while(sc.hasNext()){ int w = sc.nextInt(); int h = sc.nextInt(); int sum = 0; int w0 = w/4; int h0 = h/4; int w1 = w%4; int h1 = h%4; sum += w0*h0*8; sum += 2*w1*h0; sum += 2*h1*w0; if(w1<=2 && h1<=2){ sum += w1*h1; }else if(w1==3 && h1==3){ sum += 5; }else if(w1<=2 && h1==3){ sum += 2*w1; }else if(w1==3 && h1<=2){ sum += 2*h1; } System.out.println(sum); } } }
//package com.gulamjan.t009.不要二;
import java.util.Scanner;
public class Main {
public static void main(String[] args) {
// TODO Auto-generated method stub
Scanner in = new Scanner(System.in);
while(in.hasNext()){
int W = in.nextInt();
int H = in.nextInt();
System.out.println(cakeNum(W, H));
}
in.close();
}
public static int cakeNum(int W ,int H) {
int result = 0;
if (W % 4 == 0 || H % 4 == 0) {
result = W * H / 2;
}else {
result = W * H / 2 + 1;
}
return result;
}
}
import sys x,y=list(map(int, sys.stdin.readline().split())) if x % 4 == 0 or y % 4 == 0:print(int(x*y//2)) elif x % 2 == 0 and y % 2 == 0:print(((x*y)//2+1) + 1) else:print(x*y//2 + 1)
把图像画出来就规律就明显了
还有我感觉为什么py3每次都比py2运行时间长,都是同样的思路。
#include<iostream> #include<cstdio> using namespace std; int main(){ int len,wid; scanf("%d %d",&len,&wid); int sum=0; while(len>0&&wid>0){ int len1=len/4; int len2=len%4; int wid1=wid/4; int wid2=wid%4; if(len2>1) len2=2; if(wid2>1) wid2=2; if(wid<2||len<2) //注意特殊情况!!! sum+=(2*len1+len2)*(wid1*2+wid2); else sum+=(2*len1+len2)*(wid1*2+wid2)-(2*len1+len2-2)*(wid1*2+wid2-2); len-=2; wid-=2; } printf("%d",sum); return 0; }思路就是一圈一圈往里减少
import java.util.*; public class Main{ static class Cake { int x; int y; boolean isFlag; public Cake(int x, int y, boolean isFlag) { this.x = x; this.y = y; this.isFlag = isFlag; } public void setFlag(boolean flag) { isFlag = flag; } } static int count = 0; public static void main(String[] args) { Scanner scanner = new Scanner(System.in); int w = scanner.nextInt(); int h = scanner.nextInt(); count = w*h; List<List<Cake>> lists = new ArrayList<>(); for (int i = 0; i < h; i++) { List<Cake> list = new ArrayList<>(); for (int j = 0; j < w; j++) { list.add(new Cake(i,j,true)); } list.add(null); list.add(null); lists.add(list); } lists.add(null); lists.add(null); for (int i = 0; i < h; i++) { for (int j = 0; j < w; j++) { Cake curCake = lists.get(i).get(j); if (!curCake.isFlag ){ continue; } Cake rightCake = lists.get(i).get(j + 2); if (rightCake != null && rightCake.isFlag){ rightCake.setFlag(false); count--; } List listLevel = lists.get(i + 2); if (listLevel != null ){ Cake topCake = lists.get(i + 2).get(j); if (topCake.isFlag){ topCake.setFlag(false); count--; } } } } System.out.println(count); } }
import java.util.Scanner; /*思路:这个蛋糕要从第一个位置开始放。同时放蛋糕的情况是可以每四行一个循环,每四列一个循环。
我们可以先算出前面四行的情况,后边就是循环问题了,就都解答出来了。
其实前面四行中,前面两行的情况一样,后边两行情况也是相同的。所以就把前面两行区分为了1,2行和3,4行。
比如针对第一行:算出前面四列情况,后边就根据循环来算出这一行总的蛋糕数量。
那么第3,4行和第1,2行还有一个关系,就是sum12+sum34=纵向数量
*/ public class Main { public static void main(String[] args) { Scanner sc = new Scanner(System.in); while (sc.hasNext()) { int m = sc.nextInt(); int n = sc.nextInt(); int a = m / 4;// 横坐标除4取整 int b = m % 4;// 横坐标取余 int c = n / 4;// 纵坐标除4取整 int d = n % 4;// 纵坐标取余 int sum12 = 0;//前边两行放的蛋糕数量一样 int sum34 = 0;//3,4行蛋糕数量也一样 int sum = 0;最后的总的蛋糕数量 int sum1234 = 0;前边四行的蛋糕数量 // 先得出前四行分别的数目,首先前面两行一样,后边两行一样 // 首先是1,2两行放的蛋糕都一样 if (d == 1) { sum12 = c * 2 + 1; } else if (d == 0) { sum12 = (c - 1) * 2 + 2; } else { sum12 = c * 2 + 2; } // 然后是3,4两行,放的蛋糕都一样 sum34 = n - sum12; // 前面四行一共放蛋糕数量如下 sum1234 = 2 * (sum12 + sum34); // 前边计算了前面四行分别的数目,接下来是往纵看, if (b == 1) { sum = a * sum1234 + sum12; }else if (b == 2) { sum = a * sum1234 + 2 * sum12; }else if (b == 3) { sum = a * sum1234 + sum12 * 2 + sum34; } else { sum = a * sum1234; } System.out.println(sum); } } }
#include<bits/stdc++.h> using namespace std; const int maxn=1000+10; int done[maxn][maxn]; int main() { int w,h; scanf("%d%d",&w,&h); memset(done,0,sizeof(done)); for(int i=0;i<h;i++) for(int j=0;j<w;j++) { if(done[i][j]==0) { done[i][j]=1; done[i][j+2]=done[i+2][j]=-1; } } int solve=0; for(int i=0;i<h;i++) for(int j=0;j<w;j++) if(done[i][j]==1) solve++; cout<<solve<<endl; return 0; }
#include<iostream> using namespace std; int main() { int m, n; cin >> m >> n; int num1, num2, line1, line2; //算出两种模式,每行有多少块蛋糕 if (m % 4 == 0) num1 = num2 = m / 2; if (m % 4 == 1) { num1 = m / 2 + 1; num2 = m / 2; } if (m % 4 == 2) { num1 = (m - 2) / 2 + 2; num2 = num1 - 2; } if (m % 4 == 3) { num1 = (m - 3) / 2 + 2; num2 = num1 - 1; } //算出这两种模式分别有多少行 if (n % 4 == 0) { line1 = line2 = n/2; } if (n % 4 == 1) { line1 = n/2+1; line2 = n/2; } if (n % 4 == 2) { line1 = n/2+1; line2 =(n-2)/2 ; } if (n % 4 == 3) { line1 =(n-3)/2+2 ; line2 = line1-1; } //cout << num1 << "*" << line1 << "+" << num2 << "*" << line2 << "="; cout << num1*line1 + num2*line2; return 0; }
#include <stdio.h> int main(){ int n,m; while(scanf("%d%d",&n,&m)!=EOF){ bool mark[2000][2000]; for(int i=0;i<n;i++){ for(int j=0;j<m;j++){ mark[i][j]=false; } } int sum=0; for(int i=0;i<n;i++){ for(int j=0;j<m;j++){ if(mark[i][j]==true) continue; else{ sum++; mark[i][j]=mark[i-2][j]=mark[i+2][j]=mark[i][j-2]=mark[i][j+2]=true; } } } printf("%d\n",sum); } return 0; }
#include<iostream> using namespace std; int main() { int W,H; while(cin >> W >> H) { int divofW, divofH, modofW, modofH, cnt = 0; divofW = W / 4; divofH = H / 4; modofW = W % 4; modofH = H % 4; cnt += divofW * divofH * 2 * 4; cnt += modofW * 2 * divofH; cnt += modofH * 2 * divofW; if(modofW >= 3 && modofH >= 3) cnt += 5; else if(modofW >= 2 && modofH >=2) cnt += 4; else if((modofW == 2 && modofH ==1) || (modofW ==1 && modofH ==2)) cnt += 2; else if(modofW >=1 && moofH >= 1) cnt += 1; cout << cnt << endl; } return 0; }
import java.util.Scanner; public class Main{ public static void main(String[] args){ // 填充法, 只要当前格没有蛋糕并且其四周间隔为2的位置也没蛋糕, 就在此格子上放个蛋糕并标记 Scanner in = new Scanner(System.in); int w = in.nextInt(); int h = in.nextInt(); boolean[][] visited = new boolean[h][w]; int count = 0; for (int i = 0; i < h; ++i) { for (int j = 0; j < w; ++j) { if(visited[i][j] == true) continue; else{ if(j-2 < 0 || visited[i][j-2] != true){ if(j+2 >= w || visited[i][j+2] != true){ if(i-2 < 0 || visited[i-2][j] != true){ if(i+2 >= h || visited[i+2][j] != true){ ++count; visited[i][j] = true; } } } } } } } System.out.println(count); } }