170 похожих чатов

Всем привет, у меня есть вопрос на обсудить, про выполнение

длительных, неблокирующих операций.

Суть в том, что у меня есть однопоточное игровое ядро, очень похоже по своей сути на STA приложение вин форм. Это ядро обслуживает кучу клиентов, поэтому никогда не выполняет никаких длительных операций: т.е. у него есть входная очередь с событиями, которую оно разгребает и куча выходных очередей, в которые ядро кидает данные, которые нужно отправить игрокам.

А теперь задача: когда игрок подключается к серверу, нужно загрузить данные о нём с бд. Напрямую грузить нельзя, поэтому я сделал так, что запускается асинхронная операция загрузки, которая кидает в очередь сообщений данные о загруженном игроке. Вроде норм.

Но меня смущают некие маловероятные сценарии, типа: игрок подключился, отключился и вот наконец пришли данные о нём из базы. Или: игрок подключился, отключился, подключился и вот пришли данные о нём раз, и данные два, да ещё и порядок не детерминирован.

Для того чтобы не думать о таких сценариях, я решил что стоит сделать отмену асинхронной операции. Т.е. я говорю стороджу загрузить данные, стородж возвращает ид операции, если игрок отключился, то удаляем ид операции. Получается, что когда данные таки загрузятся из базы, можно понять нужны эти данные ещё или нет.

Отменять саму асинхронную операцию не вариант, т.к. она уже может завершиться, а данные уже попасть во входную очередь.

Проблема в том, что реализация пока получается не огонь :( а мне кажется, что проблема типовая для гуёвых программистов: типа грузим картинки в фоне, а если пользователь что-то нажал, то картинку уже не нужно грузить.

Что думаете? Может существует более простой способ, чем тот что я описал? Или есть готовые, удобные реализации, которые можно стырить?

2 ответов

13 просмотров

обычно просто используют отмену (cancellation токены), т.е. данные ты загрузил, но они не нужны уже (в токене была выставлена отмена) и дальше просто ничего не должно произойти

Мне кажется, ты правильно делаешь. Как минимум, в самом конце операции (когда ты уже завершил работу и находишься синхронно в ядре) нужно проверять, что игрок всё ещё подключен к серверу. Если не подключен — игнорировать результаты операции. Отменять in-flight операцию через cancellation token необязательно. Насколько я понимаю, ситуация это редкая, и ты рискуешь нагородить много кода ради копеечной экономии.

Похожие вопросы

Обсуждают сегодня

30500 за редактор? )
Владимир
47
а через ESC-код ?
Alexey Kulakov
29
Чёт не понял, я ж правильной функцией воспользовался чтобы вывести отладочную информацию? но что-то она не ловится
notme
18
У меня есть функция где происходит это: write_bit(buffer, 1); write_bit(buffer, 0); write_bit(buffer, 1); write_bit(buffer, 1); write_bit(buffer, 1); w...
~
13
Недавно Google Project Zero нашёл багу в SQLite с помощью LLM, о чём достаточно было шумно в определённых интернетах, которые сопровождались рассказами, что скоро всех "ибешни...
Alex Sherbakov
5
Ребят в СИ можно реализовать ООП?
Николай
33
Как передать управляющий символ в открытую через CreateProcess консоль? Собсна, есть процедура: procedure TRedirectThread.WriteData(Data: OEMString); var Written: Cardinal;...
Serjone
6
в JclConsole объявлено так: function CtrlHandler(CtrlType: DWORD): BOOL; stdcall; - где ваше объявление с stdcall? у вас на картинке нет stdcall
Karagy
8
https://github.com/erlang/otp/blob/OTP-27.1/lib/kernel/src/logger_h_common.erl#L174 https://github.com/erlang/otp/blob/OTP-27.1/lib/kernel/src/logger_olp.erl#L76 15 лет назад...
Maksim Lapshin
20
~ 2m21s  nix shell github:nixos/nixpkgs#stack ~  stack ghc -- --version error: … while calling the 'derivationStrict' builtin at /builtin/derivation.nix:...
Rebuild your mind.
6
Карта сайта