https://swexpertacademy.com/main/code/problem/problemDetail.do?contestProbId=AWXRDL1aeugDFAUo
1. BC->생성자 : 그림에 표시된 범위의 좌표를 List<int[]>에 추가
2. 리스트를 돌면서 A의 좌표와 일치된게 있다 -> BC범위 안이다 -> 기계의x,y좌표(유일성 => 식별용), power 저장, 내림차순 정렬
3. 합 갱신
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
import java.util.List;
import java.util.StringTokenizer;
public class Solution_5644_유동훈 {
static List<BC> BCs=new ArrayList<>();
static int sumA;
static int sumB;
static class info implements Comparable<info>
{
int x;//BC고유 x,y
int y;
int power;
public info(int x, int y, int power) {
super();
this.x = x;
this.y = y;
this.power = power;
}
@Override
//높은거부터 나오게 정렬
public int compareTo(info o) {
return -(this.power-o.power);
}
}
static class BC
{
int x;
int y;
int c; //충전범위
int power;
List<int[]> range=new ArrayList<>();
public BC(int x, int y, int c, int power) {
super();
this.x = x; //열
this.y = y; //행
this.c = c;
this.power = power;
//this.range.add(new int[] {x,y});
int[] arr= new int[2*c+1];
for(int i=0;i<2*c+1;++i)
{
arr[i]=i;
if(i>c) arr[i]=arr[arr.length-i-1];
}
//System.out.println(Arrays.toString(arr));
int index=0;
if(index<arr.length);
for(int i=y-c;i<=y+c;++i)
{
//int mid=x;
for(int a=x-arr[index];a<=x+arr[index];a++)
{
this.range.add(new int[] {a,i});
}
index++;
}
//System.out.println(range.get(0));
}
}
static int M; //이동수
static int BC_NUM; //BC개수
//해당시간에
static void sol(int Ax,int Ay, int Bx, int By)
{
//범위안이면
//A가 범위안인지 검사
//범위안이면 BC의 좌표, 파워 저장
boolean AisIn=false;
//List<Integer> powersA=new ArrayList<>();
//List<int[]> xyA= new ArrayList<>();
List<info> infosA=new ArrayList<>();
LOOP:for(BC item : BCs) //모든객체에대해
{
//한객체의 리스트에 대해
for(int i=0;i<item.range.size();++i)
if(item.range.get(i)[0]==Ax && item.range.get(i)[1]==Ay)
{
AisIn=true;
infosA.add(new info(item.x,item.y,item.power));
//xyA.add(new int[] {item.x,item.y});
//break LOOP;
}
}
Collections.sort(infosA);
//B검사
boolean BisIn=false;
//List<Integer> powersB=new ArrayList<>();
//List<int[]> xyB= new ArrayList<>();
List<info> infosB=new ArrayList<>();
LOOP:for(BC item : BCs) //모든객체에대해
{
//한객체의 리스트에 대해
for(int i=0;i<item.range.size();++i)
if(item.range.get(i)[0]==Bx && item.range.get(i)[1]==By)
{
BisIn=true;
infosB.add(new info(item.x,item.y,item.power));
//powersA.add(item.power);
//xyB.add(new int[] {item.x,item.y});
//break LOOP;
}
}
Collections.sort(infosB);
//파워순 내림차순 정렬
//=> 0번 인덱스가 파워 최댓값임
//A가 범위안인경우
if(AisIn)
{
//B도 안인 경우
if(BisIn)
{
//둘이 최대값이 겹침
if(infosA.get(0).x == infosB.get(0).x &&
infosA.get(0).y == infosB.get(0).y)
{
//A도 범위1개, B도범위 1개임->반반나눠가져라
if(infosA.size()==1 && infosB.size()==1)
{
sumA=sumA+infosA.get(0).power/2;
sumB=sumB+infosB.get(0).power/2;
}
//B가 양보해라
else if(infosA.size()==1 && infosB.size()>1)
{
//양보하는거랑 반반씩나누는거랑 비교할 필요X
//무조건 양보가 더 큼
//왜? 양보=원본+추가, 반반=원본/2+원본/2
sumA=sumA+infosA.get(0).power;
sumB=sumB+infosB.get(1).power;
}
//A가 양보해라
else if(infosA.size()>1 && infosB.size()==1)
{
sumA=sumA+infosA.get(1).power;
sumB=sumB+infosB.get(0).power;
}
else if(infosA.size()>1 && infosB.size()>1)
{
//A가 양보하는게 더이득
if(infosA.get(1).power>infosB.get(1).power)
{
sumA=sumA+infosA.get(1).power;
sumB=sumB+infosB.get(0).power;
}
//B가 양보하는게 더 이득
else
{
sumA=sumA+infosA.get(0).power;
sumB=sumB+infosB.get(1).power;
}
}
}
//안겹침=>각각++
else
{
sumA=sumA+infosA.get(0).power;
sumB=sumB+infosB.get(0).power;
}
}
//B는 밖인경우 A만++
else
{
sumA=sumA+infosA.get(0).power;
}
}
//A가 범위밖인 경우
else
{
//B는 안->B만 ++
if(BisIn)
{
sumB=sumB+infosB.get(0).power;
}
else
{
//nothing
}
}
//System.out.println("결과출력");
//System.out.println(sumA+" "+sumB);
/*//B가 범위안인경우
if(BisIn)
{
//A도 안인 경우
if(AisIn)
{
//앞에서 함
}
//A는 밖인경우 B만++
else
{
sumB=sumB+infosB.get(0).power;
}
}
//B가 범위밖인 경우
else
{
//아무일도안함
}*/
}
public static void main(String[] args) throws NumberFormatException, IOException {
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
StringTokenizer st;
int T= Integer.parseInt(br.readLine());
for(int test=1;test<=T;++test)
{
st= new StringTokenizer(br.readLine());
M=Integer.parseInt(st.nextToken());
BC_NUM=Integer.parseInt(st.nextToken());
List<Integer> A=new ArrayList<>();
st= new StringTokenizer(br.readLine());
for(int i=0;i<M;++i)
{
A.add(Integer.parseInt(st.nextToken()));
}
List<Integer> B=new ArrayList<>();
st= new StringTokenizer(br.readLine());
for(int i=0;i<M;++i)
{
B.add(Integer.parseInt(st.nextToken()));
}
BCs=new ArrayList<>();
for(int i=0;i<BC_NUM;++i)
{
st= new StringTokenizer(br.readLine());
int x=Integer.parseInt(st.nextToken()); //열
int y=Integer.parseInt(st.nextToken()); //행
int c=Integer.parseInt(st.nextToken());
int power=Integer.parseInt(st.nextToken());
BCs.add(new BC(x, y, c, power));
}
//입력 끝
//System.out.println((BC.get(0).range.get(index)));
int Ax=1;
int Ay=1;
int Bx=10;
int By=10;
sol(Ax,Ay,Bx,By); //초기=1,1 /10,10
for(int i=0; i<M;++i)
{
if(A.get(i)==0)
{
//아무것도안함
}
else if(A.get(i)==1)
{
//상
Ay=Ay-1;
}
else if(A.get(i)==2)
{
//우
Ax=Ax+1;
}
else if(A.get(i)==3)
{
//하
Ay++;
}
else if(A.get(i)==4)
{
//좌
Ax--;
}
if(B.get(i)==0)
{
//아무것도안함
}
else if(B.get(i)==1)
{
//상
By=By-1;
}
else if(B.get(i)==2)
{
//우
Bx=Bx+1;
}
else if(B.get(i)==3)
{
//하
By++;
}
else if(B.get(i)==4)
{
//좌
Bx--;
}
sol(Ax,Ay,Bx,By);
}
//sol(4,4,10,10);
//sol(1,1,)
System.out.println("#"+test+" "+(sumA+sumB));
sumA=0;
sumB=0;
}
}
}
'Algorithm > swea' 카테고리의 다른 글
1247. [S/W 문제해결 응용] 3일차 - 최적 경로 (0) | 2022.08.19 |
---|---|
3234. 준환이의 양팔저울 (0) | 2022.08.19 |
swea: 4012 요리사 (0) | 2022.08.12 |
1861. 정사각형 방 (0) | 2022.08.09 |
1233. [S/W 문제해결 기본] 9일차 - 사칙연산 유효성 검사 (0) | 2022.08.09 |