4

I uploaded a txt file (a maze) to my code in Python.

Example:

10 8

+-+-+-+-+-+-+-+-+-+-+
|*      |           |
+ +-+-+ +     +-+ + +
|   |         |X  | |
+-+ + +-+     +-+-+ +
|       |     |     |
+-+-+-+-+ + + +-+   +
|         | |   |   |
+ +-+-+ +-+ +-+ +   +
| |       | |   |   |
+ + +-+-+ + + +-+   +
| |   | | | |   |   |
+ +-+ + +-+ +-+ +   +
| |       | |   |   |
+ +-+-+-+-+ + +-+   +
|                   |
+-+-+-+-+-+-+-+-+-+-+

I am willing to save the first row - the dimensions of the maze. The code I wrote works only when I have one number on each dimen. How can I get the dimension no matter how many numbers in each dimen. At the example above I want to get 10 & 8.

My code:

def loadMaze(file_name):
    readIt = open(file_name, 'r')
    readLines = readIt.readlines()
    x_dim = int(readLines[0][0])
    y_dim = int(readLines[0][2])
    mazeList = [list(i.strip()) for i in readLines[1:]]
    return x_dim, y_dim, mazeList
Jiana
  • 87
  • 1
  • 5
  • Have a look at [`str.split`](https://docs.python.org/3/library/stdtypes.html#str.split) – Steve Apr 23 '21 at 14:11

4 Answers4

1

You never close the file that you open. As mentioned in the docs:

It is good practice to use the with keyword when dealing with file objects. The advantage is that the file is properly closed after its suite finishes, even if an exception is raised at some point.

The rest of your code can be accomplished succinctly with str.stplit and multiple assignment. (The underscore is assigned to the blank line between the dimensions and maze as a way of "ignoring" it, since presumably you don't want it in the maze list.)

def load_maze(file_name):
    with open(file_name) as f:
        dims, _, *maze_lines = [line.rstrip() for line in f]
    x, y = [int(dim) for dim in dims.split()]
    maze = [list(line) for line in maze_lines]
    return x, y, maze

Personally I think it might be nice to return x and y as a tuple together, like this:

return (x, y), maze

But that's up to you.

CrazyChucky
  • 3,263
  • 4
  • 11
  • 25
1

The issue with your code is that when you do readLines[0][0] what you are actually pointing to is a a character in the string. Note the ^ indicates which character you are reading.

10 8\n
^

for readLines[0][2] what you are actually pointing to is a a character in the string:

10 8\n
  ^

What you want to do is parse that line, separate on the space and treat those tokens (10 and 8) as integers. I would also recommend using "with open" since you never "close" your file. This will take that first string, split on spaces to form a list of tokens. Then you can access the numbers (as strings) and convert to integer.

def loadMaze(file_name):
    with open(file_name, 'r') as  readIt:
        readLines = readIt.readlines()
    dims = readLines[0].split()
    x_dim = int(dims[0])
    y_dim = int(dims[1])
    mazeList = [list(i.strip()) for i in readLines[1:]]
    return x_dim, y_dim, mazeList

Alternately you could do it while reading the file

def loadMaze(file_name):
    with open(file_name, 'r') as  readIt:
       dims = readIt.readline().split()
       x_dim = int(dims[0])
       y_dim = int(dims[1])
       readIt.readline() # read and skip the blank line
       mazeList = [list(i.strip()) for i in readIt.readlines()]
    return x_dim, y_dim, mazeList
Tom Myddeltyn
  • 1,307
  • 1
  • 13
  • 27
0

I don't have a lot of experience with python, but it looks like you can use the .partition() function to get the string characters up to a certain symbol. then you can use the .split() and map() functions to separate the numbers by spaces and then transform them into int

def loadMaze(file_name):
    readIt = open(file_name, 'r')
    readLines = readIt.readlines()
    partition = readLines[0].partition('+').split()
    dimensionArray = map(int, partition)
    x_dim = dimensionArray[0]
    y_dim = dimensionArray[1]
    mazeList = [list(i.strip()) for i in readLines[1:]]
    return x_dim, y_dim, mazeList

here are a few references

partition

split and map

EDIT: when looking at your file earlier, I thought the dimensions were on the same line as the start of the maze. If they aren't, you don't need the partition

def loadMaze(file_name):
    readIt = open(file_name, 'r')
    readLines = readIt.readlines()
    splitFirstLine = readLines[0].split()
    dimensionArray = map(int, splitFirstLine)
    x_dim = dimensionArray[0]
    y_dim = dimensionArray[1]
    mazeList = [list(i.strip()) for i in readLines[1:]]
    return x_dim, y_dim, mazeList
rhavelka
  • 2,283
  • 3
  • 22
  • 36
-1

Assuming the maze dimensions are always the first line of the text file, you can use the string split() method to split the first line at any whitespace, returning a list. The first element of the list is the x-dimension; the second element is the y-dimension.

>>> def load_maze(filename):
    with open(filename) as file:
        lines = file.readlines()
    return lines

>>> maze = load_maze(path)
>>> x, y = maze[0].strip().split()
>>> x, y = int(x), int(y)
>>> x, y
(10, 8)
Jacob Lee
  • 4,405
  • 2
  • 16
  • 37