본문 바로가기
Algorithm/BOJ

[BOJ]15661번: 링크와 스타트 (c++)

by HBGB 2020. 5. 21.

https://www.acmicpc.net/problem/15661

 

15661번: 링크와 스타트

첫째 줄에 N(4 ≤ N ≤ 20)이 주어진다. 둘째 줄부터 N개의 줄에 S가 주어진다. 각 줄은 N개의 수로 이루어져 있고, i번 줄의 j번째 수는 Sij 이다. Sii는 항상 0이고, 나머지 Sij는 1보다 크거나 같고, 100

www.acmicpc.net

 

#include <iostream>
#include <vector>
#include <algorithm>

using namespace std;

const int MAX = 20;
int S[MAX][MAX];
int N;
int min_dif = 2000;

// 팀의 합산 점수 구하기
int get_point(vector<int> &team)
{
	int sum = 0;
	for (int i : team)
	{
		for (int j : team)
		{
			sum += S[i][j];
		}
	}
	return sum;
}

void dfs(vector<int> &team_s, vector<int> &team_l, int index)
{
	if (index == N)
	{
		// 팀의 인원은 최소 1명 이상이어야 함
		if (team_s.size() < 1 || team_l.size() < 1)
		{
			return;
		}

		// 최소 점수차이 구하기
		min_dif = min(min_dif, abs(get_point(team_s) - get_point(team_l)));

		return;
	}

	// index번째의 선수가 team_s에 속했을 때
	team_s.push_back(index);
	dfs(team_s, team_l, index + 1);
	team_s.pop_back();

	// index번째의 선수가 team_l에 속했을 때
	team_l.push_back(index);
	dfs(team_s, team_l, index + 1);
	team_l.pop_back();
}

int main()
{
	ios_base::sync_with_stdio(0);
	cin.tie(0);
	cout.tie(0);

	// 입력
	cin >> N;
	for (int i = 0; i < N; ++i)
	{
		for (int j = 0; j < N; ++j)
		{
			cin >> S[i][j];
		}
	}

	// dfs - 백트랙킹으로 선수 조합해서 팀만들기
	vector<int> team_s, team_l;
	dfs(team_s, team_l, 0);

	cout << min_dif;
	
	return 0;
}

 

 

스타트와 링크 문제의 변형이다. 

차이점은 이번에는 팀의 인원수가 서로 다를 수 있다는 점! 뿐이다

 

dfs 종료조건에서 불가능한 케이스 부분만 좀 바꿔주면 된다. 

// 팀의 인원은 최소 1명 이상이어야 함
if (team_s.size() < 1 || team_l.size() < 1)
{
    return;
}

 

'Algorithm > BOJ' 카테고리의 다른 글

[BOJ]1248번: 맞춰봐 (c++)  (0) 2020.05.22
[BOJ]2529번: 부등호 (c++)  (0) 2020.05.21
[BOJ]14889번: 스타트와 링크 (c++)  (0) 2020.05.21
[BOJ]14501번: 퇴사 (c++)  (0) 2020.05.20
[BOJ]1759번: 암호 만들기 (c++)  (0) 2020.05.20

댓글