10543. Путешествующий политик
Политику необходимо провести не менее
k публичных выступлений. В один день
может быть произнесено не более одной речи. Если политик желает провести
несколько выступлений в одном и том же городе, то они не должны проводиться в
соседние дни, так как это будет не эффективно. Однако выступать в одном и том
же городе хотя бы через день уже эффективно.
Первая речь должна быть проведена
политиком в его родном городе, последняя – в столице. Какое наименьшее
количество выступлений необходимо провести политику, чтобы их
последовательность удовлетворяла всем выше перечисленным требованиям?
Вход. Состоит
из нескольких тестов. Первая строка каждого теста содержит три числа – n (количество городов, 2 £ n £ 50), m (количество дорог) и k (минимальное количество выступлений,
2 £ k £ 16). Следующие m строк содержат пару чисел u
и v, означающих возможность посещения
города v после u. Родной город политика имеет номер 0, столица имеет номер n – 1. Последний тест содержит три нуля
и не обрабатывается.
Выход. Для каждого теста вывести наименьшее
возможное количество выступлений. Если это совершить невозможно, то вывести
“LOSER”. Если требуемое количество выступлений будет больше 20, то вывести
также “LOSER”.
3 3 3
0 1
0 2
1 2
5 6 5
0 1
0 3
1 2
2 4
3 2
3 4
3 3 10
0 1
1 0
1 2
0 0 0
Пример выхода
3
LOSER
11
РЕШЕНИЕ
графы, количество путей
между вершинами
Задача состоит в том, чтобы найти
наименьшее (p < 21), для которого значение
Ap–1[0][n – 1] будет не нулевым (0 – начальный город, (n – 1) – последний город, столица).
Карта страны для третьего теста
имеет вид:
Чтобы
совершить как минимум 10 выступлений, начиная в городе 0 и заканчивая в 2,
необходимо сделать 11 следующих выступлений: 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 2.
Матрицу смежности графа храним в
массиве mas. Массив temp будет использоваться при умножении матриц.
int mas[50][50], temp[50][50];
Читаем
данные текущего теста. Заполняем матрицу смежности mas.
while(scanf("%d
%d %d",&n,&m,&k),n + m + k)
{
memset(mas,0,sizeof(mas));
for(i = 0; i
< m; i++)
{
scanf("%d
%d",&a,&b);
mas[a][b] = 1;
}
Скопируем данные массива mas в
temp. Далее в temp будет храниться начальное состояние массива mas. В то время
как массив mas будет последовательно хранить temp, temp2, temp3,
и так далее.
memcpy(temp,mas,sizeof(mas));
Вычисляем mas = tempk
– 1 (для этого следует осуществить k
– 2 матричных умножений).
for(i = 1; i
< k - 1; i++) mult();
Пока k < 21
(количество выступлений не более 20) и мы еще не дошли до n – 1 - го города (столицы), совершаем еще одно выступление,
увеличивая k на 1 и соответственно
пересчитывая mas = mas * temp при помощи функции mult.
while ((k
< 21) && (!mas[0][n-1]))
{
mult(); k++;
}
Выводим ответ согласно условию
задачи.
if (k == 21)
printf("LOSER\n");
else
printf("%d\n",k);
Функция
mult совершает умножение mas = mas * temp
void mult(void)
{
int i, j, k,
s;
int
m1[50][50];
for(i = 0; i
< n; i++)
for(j = 0; j
< n; j++)
{
s = 0;
for(k = 0;
k < n; k++)
s += mas[i][k] * temp[k][j];
m1[i][j] = s;
}
memcpy(mas,m1,sizeof(m1));
}