Я бы наложил еще одну 2D-сетку с отдельными байтами. Каждый бит байта соответствует возможному направлению входа, где 1 означает, что по нему можно пройти с этого направления, а 0 означает, что нет. Затем вы можете проверить возможность ввода с помощью бинарной маскировки.
Если в большинство ваших ячеек можно войти с любого направления, вы можете рассмотреть возможность использования карты с абсолютный идентификатор тайла (например, X*MaxY+Y) в качестве ключа и описанная выше байтовая схема, указывающая на возможность ввода. Это медленнее для доступа, но занимает меньше места.
Например, пусть направления изложены так:
Bit # X offset Y offset
123 -1 0 1 -1 -1 -1
4 5 -1 0 1 0 0 0
678 -1 0 1 1 1 1
Если я иду в северо-восточном направлении, это соответствует биту № 3. Я могу выполнить маскирование, переведя приведенные выше значения в битовые маски:
1 2 4
8 16
32 64 128
Я могу войти с направления, если следующее возвращает true
Enterability(CurrentX+Xoffset(Dir), CurrentY+Yoffset(Dir)) & BitMask(Dir)
(Извините, боюсь, я недостаточно хорошо знаю Lua, чтобы написать это на этом языке)
Изменить
Итак, скажем, мои направления такие же, как указано выше, и мне нужна площадь, на которую можно войти только с севера. Для этого я устанавливаю бит №2:
Enterability(X)=2
Если мне нужна площадь, в которую можно войти как с севера, так и с юго-запада, я бы использовал:
Enterability(X)=2 | 64
где |
— операция побитового ИЛИ.
Если я хочу, чтобы в квадрат можно было войти с любого направления, кроме западного, я использую:
Enterability(X)=(~8)
где ~
— операция «не».
Если мне нужно закрыть дверь, скажем, на восток, я могу отключить этот бит:
Enterability(X)=Enterability(X) & (~16)
Чтобы снова открыть дверь, я использую:
Enterability(X)=Enterability(X) | 16
или, проще говоря,
Enterability(X)|=16
~16
создает битовое поле, состоящее из единиц, кроме бита, относящегося к 16. Использование этого с оператором AND (&
) оставляет все биты включенными, кроме одного, относящегося к 16.
Также обратите внимание, что шестнадцатеричная адресация может быть более удобной:
Decimal Hexadecimal
1 2 4 0x1 0x2 0x4
8 16 = 0x8 0x10
32 64 128 0x20 0x40 0x80
person
Richard
schedule
15.10.2012