SRM 392 에디토리얼 쓰는 김에 div2의 editorial도 활성화되길 바라는 마음에서 div2까지 씁니다.
Easy (250 pts.)
문제 설명
2007년 1월 1일에 만들어진 캔디들이 있습니다. 이 캔디를 매 월말에 먹었을 때 캔디의 평균적인 수명을 구해야 합니다.
[spoiler="더 보기..."]
문제 해법
그냥 계산하시면 됩니다. 저는 floating point error를 피하기 위해서 int로 계산했습니다.
~~~ cpp
double getAverage(vector eatenCandies)
{
int i;
int d = 0;
int dates[] = {31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};
int tot = 0, candies = 0;
for (i = 0; i < 12; i++)
{
d += dates[i];
tot += eatenCandies[i] * d;
candies += eatenCandies[i];
}
return double(tot) / double(candies);
}
[/spoiler]
Medium (500 pts.)
* div1의 easy와 같은 문제입니다. div1의 editorial을 참조하세요.
Hard (1000 pts.)
* 문제 설명
n by n의 table을 [0, d)의 숫자들로 채우려 합니다. 한 row나 column에는 반드시 한 숫자가 최소한 한번 나와야 합니다.
이를 만족하는 table들 중 "사전순으로 가장 작은" 것을 찾아야 합니다.
[spoiler="더 보기..."]
* 문제 해법
예제를 보시면 알겠지만 가장 위와 왼쪽 줄은 (0 .. 0) 1 2 3 ... d 와 같은 식으로 채우는 것이 가장 좋습니다.
그 후에 나머지 오른쪽 아래 공간은 모든 숫자가 한 번씩만 사용될 수 있다는 것을 이용해서 백트래킹으로 구할 수 있습니다.
~~~ cpp
int table[50][50];
int usex[50][50];
int usey[50][50];
class QuasiLatinSquares
{
public:
int N, D;
bool solve(int x, int y)
{
if (y == N) return solve(x + 1, 0);
if (x == N) return true;
if (table[x][y] != -1) return solve(x, y + 1);
for (int l = 0; l < D; l++)
{
if (usex[x][l] == 0 && usey[y][l] == 0)
{
usex[x][l] = usey[y][l] = 1;
table[x][y] = l;
if (solve(x, y + 1)) return true;
table[x][y] = -1;
usex[x][l] = usey[y][l] = 0;
}
}
return false;
}
vector<string> makeSquare(int n, int d)
{
N = n; D = d;
vector<string> ret;
int i, j, k = n - d + 1;
fill(table[0], table[n], -1);
for (i = 0; i < k; i++)
{
for (j = 0; j < k; j++)
table[i][j] = 0;
for (j = k; j < n; j++)
{
table[i][j] = table[j][i] = j - k + 1;
usex[j][j - k + 1] = usey[j][j - k + 1] = 1;
}
}
solve(0, 0);
for (i = 0; i < n; i++)
{
char cc[100];
char *s = cc;
for (j = 0; j < n; j++)
{
sprintf(s, "%d ", table[i][j]);
while (*s != 0) s++;
}
s--;
*s = 0;
ret.push_back(cc);
}
return ret;
}
};
Toivoa
SRM 392 에디토리얼 쓰는 김에 div2의 editorial도 활성화되길 바라는 마음에서 div2까지 씁니다.
Easy (250 pts.)
double getAverage(vector eatenCandies)
{
int i;
int d = 0;
int dates[] = {31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};
int tot = 0, candies = 0;
for (i = 0; i < 12; i++)
{
d += dates[i];
tot += eatenCandies[i] * d;
candies += eatenCandies[i];
}
return double(tot) / double(candies);
}
[/spoiler]
16년 전