2013-03-21 3 views
1

Я пытаюсь проверить простой 2d-координатный координатор координат в python. Он создает объекты Tile с массивами x и y, чтобы я мог получить доступ к координатам и изменить их свойства.Python, индекс индекса вне диапазона

Это создает объект карты и заполняет его с плиткой в ​​2D плоскости координат

map = [[ Tile(True) 
    for y in range(MAP_HEIGHT) ] 
     for x in range(MAP_WIDTH) ] 

Класс плитки:

class Tile: 
    #a tile of the map and its properties 
    def __init__(self, blocked, type, owner, block_sight = None): 
     self.blocked = blocked 
     self.type = type 
     self.owner = owner 
     if block_sight is None: block_sight = blocked 
     self.block_sight = block_sight 

Я попытался иметь программу чтения текстового файла посимвольно для создания карты. Он будет вставлять объект в координаты, предоставленные mapx и mapy, в карту.

mapx = 0 
mapy = 0 
filename = str(mapn) + '.txt' 
new_map = [[ Tile(True, 0, 0) 
     for y in range(MAP_HEIGHT) ] 
     for x in range(MAP_WIDTH) ] 
with open(filename) as f: 
    while True: 
     c = f.read(1) 
     if not c: 
      return new_map 
     elif (c == '#'): 
      new_map[mapx][mapy].blocked = False 
      new_map[mapx][mapy].block_sight = True 
      new_map[mapx][mapy].type = 0 
      new_map[mapx][mapy].owner = 0 

(После еще нескольких elifs)

if(mapx < MAP_WIDTH): 
    mapx += 1 
elif(mapy < MAP_HEIGHT): 
    mapy += 1 
    mapx = 0 

При запуске этого я получаю эту ошибку: IndexError: индексный список из диапазона. Это говорит линия

new_map[mapx][mapy].blocked = False 

является вину за это. Любая идея, что я делаю неправильно?

+0

Вы можете показать * минимальный * пример, который показывает вашу проблему? В противном случае единственное, что мы можем сказать, это то, что вы не можете правильно проверить, когда индекс находится в зоне действия. – Bakuriu

+0

Вы уверены, что ваш файл имеет именно символы 'mapx * mapy'? – tom

+0

@tom О да. Если в файле больше строк, то «mapx» никогда не будет сброшено до «0», а в следующем цикле его значение будет «MAP_WIDTH», которое выходит за пределы диапазона. Добавление 'else: break' или' else: mapx = 0' должно решить 'IndexError' (хотя я думаю, что есть более умный способ прочитать этот файл, чтобы избежать этой вещи). – Bakuriu

ответ

2

После инициализации внешний список будет иметь MAP_WIDTH элементов с индексами от 0 до MAP_WIDTH-1. Аналогично, каждый внутренний список будет иметь индексы от 0 до MAP_HEIGHT-1.

Рассмотрите, что произойдет, когда mapx = MAP_WIDTH-1; т.е. находится в конце списка с помощью кода:

if(mapx < MAP_WIDTH): 
    mapx += 1 
.... 

Значение mapx станет больше, чем верхняя граница списка.

Для решения этой проблемы необходимо провести тестирование mapx < MAP_WIDTH-1. Тестирование в elif также необходимо соответствующим образом изменить.

0

Это было бы более pythonic, если вы сначала прочитали файл и создали список [... (xi, yi) ...], а затем создали цикл над (xi, yi), чтобы инициализировать объекты Tile. Таким образом, вам не придется думать о индексах списка.

Just my 2 cts ...