树莓派Tetris AI观测空间报错求助:多维度数组创建失败
Let's break down your problem and fix it step by step—those errors are happening because your observation space setup doesn't match the structure of your actual game state, and how RL frameworks expect discrete spaces to work.
Why the Errors Occur
1. IndexError: too many indices for array (with large Discrete values)
spaces.Discrete(n) is designed for single integer values—each observation is just one number between 0 and n-1. When you set self.observation_space = spaces.Discrete(8*16*7*4*8), you're telling the framework your entire game state is encoded as a single big integer. But your code is probably trying to index this integer like a multi-dimensional array (e.g., observation[row][col] to access a board cell), which doesn't work—integers are scalars, not arrays, hence the "too many indices" error.
2. IndexError: index 1 is out of bounds... (with Discrete(1) or Discrete(2))
A Discrete(1) space only allows the value 0, and Discrete(2) only allows 0 and 1. But your actual game state has way more possible variations (7 block types, 4 rotations, 8 stored block options, plus the full board state). When your code tries to pass an observation value outside these tiny ranges, you get an out-of-bounds error.
Correct Observation Space Setup
Your observation has multiple distinct components: the board state, current block type, current rotation, and stored block. You need a composite space to represent these, not a single Discrete space. Here are the best options:
Option 1: Use spaces.Dict (Most Readable)
This lets you name each component, making your code easier to debug and maintain:
import gymnasium as gym # or gym, depending on your framework from gymnasium import spaces import numpy as np # Define each component of the observation board_space = spaces.Box( low=0, high=7, # 0 = empty cell, 1-7 = block types shape=(16, 8), # height x width of your Tetris board dtype=np.int32 ) current_block_space = spaces.Discrete(7) # 7 unique block types current_rotation_space = spaces.Discrete(4) # 0°, 90°, 180°, 270° stored_block_space = spaces.Discrete(8) # 7 block types + "no stored block" # Combine into a structured Dict space self.observation_space = spaces.Dict({ "board": board_space, "current_block": current_block_space, "current_rotation": current_rotation_space, "stored_block": stored_block_space })
When generating observations, pass a dictionary matching this structure:
observation = { "board": your_16x8_board_array, "current_block": current_block_id, # 0-6 "current_rotation": rotation_id, # 0-3 "stored_block": stored_block_id # 0-7 (map to your 8 options) }
Option 2: Use spaces.Tuple (Simpler for Basic Workflows)
If you prefer a lightweight tuple structure instead of named keys:
self.observation_space = spaces.Tuple([ spaces.Box(low=0, high=7, shape=(16, 8), dtype=np.int32), spaces.Discrete(7), spaces.Discrete(4), spaces.Discrete(8) ])
Your observation will then be a tuple like (board_array, block_id, rotation_id, stored_block_id).
Option 3: Flatten to a Single Box Space (For Algorithms Needing Flat Inputs)
If your RL algorithm expects a 1D array input, flatten all components into one Box space:
# Total flattened size: 16*8 (board) + 1 (block) + 1 (rotation) + 1 (stored) = 131 flat_size = 16*8 + 3 # Define min/max values for each position in the flat array low = np.zeros(flat_size, dtype=np.int32) high = np.concatenate([ np.full(16*8, 7), # Board cells range 0-7 [6], # Current block ranges 0-6 [3], # Rotation ranges 0-3 [7] # Stored block ranges 0-7 ]) self.observation_space = spaces.Box(low=low, high=high, dtype=np.int32)
When generating observations, flatten your board array and append the other values into a single 1D array.
Key Takeaway
spaces.Discrete works great for your action space (since each action is one of 6 distinct options), but it's not meant for multi-component observations. Use composite spaces like Dict, Tuple, or a flattened Box to match the structure of your game state—this will eliminate those index errors entirely.
内容的提问来源于stack exchange,提问作者J.Doe




