Форум программистов, компьютерный форум, киберфорум
С++ для начинающих
Войти
Регистрация
Восстановить пароль
Карта форума Темы раздела Блоги Сообщество Поиск Заказать работу  
 
 
Рейтинг 4.62/13: Рейтинг темы: голосов - 13, средняя оценка - 4.62
0 / 0 / 0
Регистрация: 25.11.2022
Сообщений: 19
1

Определить количество клеток, в которых убран весь мусор

10.09.2024, 16:30. Показов 2655. Ответов 31
Метки нет (Все метки)

Author24 — интернет-сервис помощи студентам
Однажды, после неудачно написанного контеста на Codeforces, Михаил окончательно разочаровался в своей карьере спортивного программиста и решил устроиться на работу дворником. Однако, даже на такую должность его ждало собеседование.

В качестве собеседования Михаилу предложили очистить от мусора довольно большой двор. Для удобства представим двор как прямоугольную таблицу, состоящую из n строк и m столбцов. Строки пронумерованы сверху вниз числами от 1 до n, а столбцы — слева направо числами от 1 до m. На пересечении i-й строки и j-го столбца находится клетка с координатами (i,j).Изначально в каждой клетке двора лежит огромная куча мусора. Михаил в рамках своего собеседования произвел k
операций, каждая из которых была одного из двух типов:

Убрать весь мусор во всех клетках
(i,j), таких что i+j=s;
Убрать весь мусор во всех клетках (i,j), таких что i−j=d.
Ваша задача — определить количество клеток, в которых Михаил убрал весь мусор.
Формат входных данных
Первая строка содержит два целых числа n и m (1≤n,m≤10**9) — размеры двора. Вторая строка содержит одно целое число k(0≤k≤300000) — количество операций, совершенных Михаилом.

Каждая из следующих k строк содержит описание очередной операции, совершенной Михаилом в следующем формате:
+ s (2≤s≤n+m) — данная операция означает, что Михаил убрал весь мусор во всех клетках (i,j), таких что i+j=s;
- d(1−m≤d≤n−1)— данная операция означает, что Михаил убрал весь мусор во всех клетках (i,j), таких что i−j=d.

Формат выходных данных
Выведите одно целое число — количество клеток, в которых Михаил убрал весь мусор.

Примеры
Входные данные
4 4
4
+ 4
+ 2
- 0
- -3
Выходные данные
7
Примечания
Рассмотрим действия Михаила в примере из условия:

Михаил убирает мусор из клеток (i,j), для которых i+j=4. Это клетки с координатами (1,3), (2,2) и (3,1).
Михаил убирает мусор из клеток (i,j), для которых i+j=2. Это клетка с координатами (1,1).
Михаил убирает мусор из клеток (i,j), для которых i−j=0. Это клетки с координатами (1,1), (2,2), (3,3) и (4,4).
Михаил убирает мусор из клеток (i,j), для которых i−j=−3. Это клетка с координатами (1,4).
Таким образом, мусор был убран из клеток (1,1), (1,3), (1,4), (2,2), (3,1), (3,3) и (4,4).

Написал код на с++, но он падает по времени на 17 тесте, кто может помочь с оптимизацией)
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
#include <bits/stdc++.h>
using namespace std;
struct cell_hash {
    size_t operator()(const pair<long long, long long>& cell) const {
        return hash<long long>()(cell.first) ^ hash<long long>()(cell.second);
    }
};
 
int main() {
    ios_base::sync_with_stdio(false);
    cin.tie(NULL);
    long long n, m, k;
    cin >> n >> m >> k;
    unordered_set<pair<long long, long long>, cell_hash> vec;
    for (long long i = 0; i < k; ++i) {
        char op;
        long long val;
        cin >> op >> val;
        if (op == '+') {
            for (long long j = 1; j <= n; ++j) {
                long long i = val - j;
                if (i >= 1 && i <= m) {
                    vec.insert({j, i});
                }
            }
        } else if (op == '-') {
            for (long long j = 1; j <= n; ++j) {
                long long i = j - val;
                if (i >= 1 && i <= m) {
                    vec.insert({j, i});
                }
            }
        }
    }
    cout << vec.size() << endl;
    return 0;
}
0
Programming
Эксперт
94731 / 64177 / 26122
Регистрация: 12.04.2006
Сообщений: 116,782
10.09.2024, 16:30
Ответы с готовыми решениями:

Закрасить минимальное количество клеток, так, чтобы множество черных клеток стало выпуклым
Здравствуйте ! Задача: Рассмотрим бесконечный лист клетчатой бумаги. Закрасим некоторое...

Определить количество раскрасок полоски из N клеток
Добрый день, решаю задачку, не могу понять почему она работает, но не правильно, помогите...

Определить количество пустых клеток, которые не бьются ни одной из фигур
В чем проблема решения? Падает на 7 тесте. Открытые тесты решает, а вот когда загружаю то где-то...

Определить количество клеток шарфа которые покрашены в заданный цвет
Незаметно для друга Алиса узнала, что ему большего всего нравятся k различных цветов. Алиса приняла...

31
Модератор
Эксперт С++
13698 / 10902 / 6471
Регистрация: 18.12.2011
Сообщений: 29,105
11.09.2024, 07:08 2
Цитата Сообщение от Artem Ka Посмотреть сообщение
C++
1
2
3
4
5
6
for (long long j = 1; j <= n; ++j) {
     long long i = val - j;
     if (i >= 1 && i <= m) {
        vec.insert({j, i});
     }
}
можно заменить на
C++
1
2
for (long long j = val-m; j<val; ++j) 
     vec.insert({j, val-j});
Аналогично 2-е условие
C++
1
2
for (long long j = val+1;  j<=m-val; ++j) 
     vec.insert({j, j-val});
0
0 / 0 / 0
Регистрация: 25.11.2022
Сообщений: 19
11.09.2024, 07:20  [ТС] 3
Спасибо, но тут уже идея плохая. Я написал по другому. И упало на 47 тесте. Ваше оптимизация вообще выдает неверный ответ).
Буду благодарен вашим идеям по решению =).
0
573 / 475 / 99
Регистрация: 05.08.2022
Сообщений: 2,598
11.09.2024, 08:08 4
Могут ли s и d повторяться в очереди операций?
0
Модератор
Эксперт С++
13698 / 10902 / 6471
Регистрация: 18.12.2011
Сообщений: 29,105
11.09.2024, 09:00 5
Цитата Сообщение от Artem Ka Посмотреть сообщение
тут уже идея плохая
Идея хорошая,
она существенно сокращает количество итераций.
Проверьте только, правильно ли я написал граничные условия (+-1, <,<=).
0
573 / 475 / 99
Регистрация: 05.08.2022
Сообщений: 2,598
11.09.2024, 09:26 6
Мне думается, что можно обойтись без двумерного массива пересечений.
Надо разложить операции на два set:
операции "+" в set+ (только значения s)
операции "-" в set- (только значения d)

Далее идём по set+ и просто суммируем количество ячеек, которые закрывают эти операции.
У меня вышли такие формулы, но не уверен (E - общая сумма закрытых ячеек):

Для каждого s:
E += min(n, m, s-1), если s <= max(n, m) + 1
E += max(n, m) - s + min(n, m) + 1, иначе
Миниатюры
Определить количество клеток, в которых убран весь мусор  
0
573 / 475 / 99
Регистрация: 05.08.2022
Сообщений: 2,598
11.09.2024, 09:33 7
Операции d - они идут "поперёк" операций s, это, конечно, подгадили знатно. Поменять бы i и j местами в разнице -вообще бы шоколад получился.

Ну ладно, раз так - то идём по set-
С одной стороны, для d можно и нужно вывести аналогичные формулы "сколько ячеек какая d добавит".
Но дополнительно нужно вывести формулу "соответствия d и s (через n и m)", и для каждой d искать в set+ есть ли там "соответствующий s". Если есть - то добавлять не просто E+= по формулам d, а вычитать по единице для каждого найденного "соответствия" d и s.

В итоге у нас будет только 1 цикл (ну или два, тут как посмотреть) и только по количеству операций k, а циклов по n и m вовсе не будет.

Но формулы для учета операций из set- мне уже выводить лень.
0
0 / 0 / 0
Регистрация: 25.11.2022
Сообщений: 19
11.09.2024, 17:10  [ТС] 8
да, конечно могут

Добавлено через 2 минуты
Ну, это решение в лоб. А они как правило неэффективны. Я поигрался с границами. Но не смог решить проблему неверного ответа

Добавлено через 6 минут
то есть первые формулы неверны?
0
573 / 475 / 99
Регистрация: 05.08.2022
Сообщений: 2,598
11.09.2024, 18:39 9
Цитата Сообщение от Artem Ka Посмотреть сообщение
то есть первые формулы неверны?
Это сейчас кому про что вопрос?
0
Модератор
Эксперт С++
13698 / 10902 / 6471
Регистрация: 18.12.2011
Сообщений: 29,105
11.09.2024, 18:40 10
Цитата Сообщение от Artem Ka Посмотреть сообщение
Я поигрался с границами
вот тут я ошибся:
Цитата Сообщение от zss Посмотреть сообщение
for (long long j = val+1; j<=m-val; ++j)
условие j-val<=m
т.е j<=m+val
0
0 / 0 / 0
Регистрация: 25.11.2022
Сообщений: 19
11.09.2024, 19:28  [ТС] 11
все равно неверный выдает. 12. но я потыкал, стало выводить 6 и 8, но никак не 7.
Цитата Сообщение от zss Посмотреть сообщение
условие j-val<=m
т.е j<=m+val
Добавлено через 51 секунду
Цитата Сообщение от KSergey9 Посмотреть сообщение
Это сейчас кому про что вопрос?
на ваш первый ответ. Я так понял алгоритм обломался где формулы?
0
Модератор
Эксперт С++
13698 / 10902 / 6471
Регистрация: 18.12.2011
Сообщений: 29,105
11.09.2024, 20:27 12
Цитата Сообщение от Artem Ka Посмотреть сообщение
все равно неверный выдает. 12
Еще надо проверить границы 1<=j<=n, получается
C++
1
2
3
4
5
6
7
        if (op == '+') {
            for (long long j = max(1,val-m); j<=min(n,val-1); ++j) 
                vec.insert({j, val-j});
        } else if (op == '-') {
            for (long long j = max(1,val+1);  j<=min(n,m+val); ++j) 
                vec.insert({j, j-val});
        }
0
0 / 0 / 0
Регистрация: 25.11.2022
Сообщений: 19
11.09.2024, 20:44  [ТС] 13
Цитата Сообщение от zss Посмотреть сообщение
if (op == '+') {
            for (long long j = max(1,val-m); j<=min(n,val-1); ++j)
                vec.insert({j, val-j});
        } else if (op == '-') {
            for (long long j = max(1,val+1);  j<=min(n,m+val); ++j)
                vec.insert({j, j-val});
        }
код все равно падает на 17 тесте.
0
28 / 18 / 11
Регистрация: 28.08.2024
Сообщений: 37
11.09.2024, 20:52 14
Artem Ka, Решил задачу на Python, могу скинуть код
1
0 / 0 / 0
Регистрация: 11.09.2024
Сообщений: 4
11.09.2024, 21:05 15
Whabablca, Быстрым решением?
0
0 / 0 / 0
Регистрация: 25.11.2022
Сообщений: 19
11.09.2024, 21:06  [ТС] 16
Цитата Сообщение от Whabablca Посмотреть сообщение
Решил задачу на Python, могу скинуть код
Ну спасибо) Давайте посмотрим.
0
28 / 18 / 11
Регистрация: 28.08.2024
Сообщений: 37
11.09.2024, 21:06 17
aqsdds, Да
0
0 / 0 / 0
Регистрация: 11.09.2024
Сообщений: 4
11.09.2024, 21:08 18
Whabablca, какая у тебя идея?
0
0 / 0 / 0
Регистрация: 25.11.2022
Сообщений: 19
11.09.2024, 21:09  [ТС] 19
Цитата Сообщение от aqsdds Посмотреть сообщение
ебя идея?
ты мой собрат по несчастью?
0
0 / 0 / 0
Регистрация: 11.09.2024
Сообщений: 4
11.09.2024, 21:10 20
Artem Ka, Есть такое
0
11.09.2024, 21:10
IT_Exp
Эксперт
87844 / 49110 / 22898
Регистрация: 17.06.2006
Сообщений: 92,604
11.09.2024, 21:10
Помогаю со студенческими работами здесь

Определить, через сколько часов количество амеб достигнет 50 клеток?
Амеба каждые 3 часа делится на 2 клетки. Через сколько часов количество амеб достигнет 50 клеток?

Найдите максимальную красоту среди красот всех клеток и количество клеток, имеющих такую красоту
Помогите с Олимпиадой задачкой. Проходит не все тесты: Видимость звездочек (упрощенная версия) ...

Определить, какое количество клеток шахматного поля не заняты и не находятся под боем
Дано шахматное поле n×n. На поле расположено m коней. Определить, какое количество клеток не заняты...

Определить, какое количество клеток шахматного поля не заняты и не находятся под боем
Дано шахматное поле n×n. На поле расположено m ладей. Определить, какое количество клеток не заняты...

Задача "Монополия": Определите условия, при которых игрок пройдет максимальное количество клеток.
У меня задача такая: Пусть есть некоторое закольцованное игровое поле и набор правил для...

Определить, какое количество клеток шахматного поля не заняты и не находятся под боем коней
Дано шахматное поле n×n. На поле расположено m коней. Определить, какое количество клеток не заняты...

Убрать весь мусор с распарсеной страницы HtmlAgilityPack
У меня есть уже страница, которую я удачно расспарсил Текст мой находиться в &quot;//div&quot;. Я его...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
20
Ответ Создать тему
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2024, CyberForum.ru