One approach to a multilayered map would be an array (or 2-dimensional array) of linked lists or vectors holding tile objects. So your tile struct would either hold a pointer to the next tile above it, or you would have "stacks" of tiles of varying heights spread across the grid. Essentially that creates a 3D array.
A nice, albeit old article on multilayered maps would be here: http://www-cs-students.stanford.edu/~amitp/Articles/Tiletech.html
So for example, your tile struct would look like something along these lines:
struct Tile
{
unsigned char type;
Tile * next = NULL;
};
The map it self, if for example it was a 2D grid, would look like this:
Tile tile_map[rows][cols];
To then get a tile at a certain point to check whether it collides or not, you would iterate through the list at that point until you reached the desired z position.
unsigned char getTileType(int x, int y, int z)
{
//Assuming 0 means an empty (air) tile
unsigned char tile_type = 0;
Tile * tile = tile_map[x][y];&tile_map[x][y];
//Iterate through the linked list of tiles at this position
int height = 0;
while (height < z && tile)
{
tile = tile -> next;
if (!tile)
return tile_type;
++height;
}
if (tile)
tile_type = tile -> type;
return tile_type;
}