How to map out a maze as a robot? - algorithm

First - I've looked through similar looking questions but they did not solve my problem, this is no repetition (I hope).
I'm building and programming a robot with an Arduino Nano that is supposed to solve a maze. It gets put somewhere in the maze and then has to find an item. The next time it is supposed to go straight to the item (it does not have to be the shortest way but no dead ends allowed).
It is not necessary to know the whole maze because as long as he has one way to the item it is good. As I said, I don't need the shortest way.
The maze is 2D, I just put black tape on a white table and the robot is supposed to use a line sensor to follow the lines.
There are no other sensors to orientate himself. First I thought of making an 2D array and each field of the maze a field in there. But since it's just a normal line sensor the robot doesn't know if a straight line is one or two fields long and the whole thing does not work.
I also tried DFS or something like that but a similar problem here. The maze is circular and how is the robot supposed to know the Node was already found before and it is the same?
It would be nice if anyone had an idea!

Although orientation is a little bit fuzzy it is possible by using the decisions. A decision has to be reproducable. It could be represented by a class:
public class Decision {
boolean[] directions = new boolean[2]; // 0 = left, 1 = straight, 2 = right
// at least 2 of them should be true or it is no decision
int path; // 0-2 to mark the current path
}
Create a stack of decisions.
If there is only one possible direction at the beginning (back doesn't count and is treated later), then move forward until you meet the first decision.
Push the decision with all possible directions on the stack.
Set path to the first possible direction and move that way.
If you end up with another decision: continue at 3.
If you find the token: abort, you found a reproducible way without dead-ends.
If it is a dead-end: return to the previous decision node (the first one one the way back) and continue with 6.
Pop the decision and try the next possible direction (set the new path and push the decision) and continue at 5.
Unless you have tried all directions, then move back another decision and continue with 6.
If there are no more decisions (the special case mentioned above, we went in the wrong direction at the beginning): move forward until you meet the first decision and continue at 3. This means you need another boolean variable to indicate if you should go backwards right at the beginning.
You have to be careful when coming back from left and want to try straight next you would have to turn left and don't go straight. So there is a little calculation involved.
The algorithm has a problem for loop shaped decisions if you start the wrong way at the beginning. I think this could be escaped by setting an upper boundary, e.g. if you still haven't found the token and met 30 decision nodes (going forward), then you are probably running in circles, so go back to start and now instead of trying the directions in increasing order, try them in decreasing order.

Related

Fill all connected grid squares of the same type

Foreword: I am aware there is another question like this, however mine has very specific restrictions. I have done my best to make this question applicable to many, as it is a generic grid issue, but if it still does not belong here, then I am sorry, and please be nice about it. I have found in the past stackoverflow to be a very picky and hostile environment to question askers, but I'm hoping that was just a bad couple people.
Goal(abstract): Check all connected grid squares in a 3D grid that are of the same type and touching on one face.
Goal(specific/implementation): Create a "fill bucket" tool in Minecraft with command blocks.
Knowledge of Minecraft not really necessary to answer, this is more of an algorithm question, and I will be staying away from Minecraft specifics.
Restrictions: I can do this in code with recursive functions, but in Minecraft there are some limitations I am wondering if are possible to get around. 1: no arrays(data structure) permitted. In Minecraft I can store an integer variable and do basic calculations with it (+,-,*,/,%(mod),=,==), but that's it. I cannot dynamically create variables or have the program create anything with a name that I did not set out ahead of time. I can do "IF" and "OR" statements, and everything that derives from them. I CANNOT have multiple program pointers - that is, I can't have things like recursive functions, which require a program to stop executing, execute itself from beginning to end, and then resume executing where it was - I have minimal control over the program flow. I can use loops and conditional exits (so FOR loops). I can have a marker on the grid in 3D space that can move regardless of the presence of blocks (I'm using an armour stand, for those who know), and I can test grid squares relative to that marker.
So say my grid is full of empty spaces only. There are separate clusters of filled squares in opposite corners, not touching each other. If I "use" my fillbucket tool on one block / filled grid square, I want it to use a single marker to check and identify all the connected grid squares - basically, I need to be sure that it traverses the entire shape, all the nooks and crannies, but not the squares that are not connected to that shape. So in the end, one of the two clusters, from me only selecting a single square of it, will be erased/replaced by another kind of block, without affecting the other blocks around it.
Again, apologies if this doesn't belong here. And only answer this if you WANT to tackle the challenge - it's not important or anything, I just want to do this. You don't have to answer it if you don't want to. Or if you can solve this problem for a 2D grid, that would be helpful as well, as I could possibly extend that to work for 3D.
Thank you, and if I get nobody degrading me for how I wrote this post or the fact that I did, then I will consider this a success :)
With help from this and other sources, I figured it out! It turns out that, since all recursive functions (or at least most of them) can be written as FOR loops, that I can make a recursive function in Minecraft. So I did, and the general idea of it is as follows:
For explaining the program, you may assuming the situation is a largely empty grid with a grouping of filled squares in one part of it, and the goal is to replace the kind of block that that grouping is made of with a different block. We'll say the grouping currently consists of red blocks, and we want to change them to blue blocks.
Initialization:
IDs - A objective (data structure) for holding each marker's ID (score)
numIDs - An integer variable for holding number of IDs/markers active
Create one marker at selected grid position with ID [1] (aka give it a score of 1 in the "IDs" objective). This grid position will be a filled square from which to start replacing blocks.
Increment numIDs
Main program:
FOR loop that goes from 1 to numIDs
{
at marker with ID [1], fill grid square with blue block
step 1. test block one to the +x for a red block
step 2. if found, create marker there with ID [numIDs]
step 3. increment numIDs
[//repeat steps 1 2 and 3 for the other five adjacent grid squares: +z, -x, -z, +y, and -y]
delete stand[1]
numIDs -= 1
subtract 1 from every marker's ID's, so that the next marker to evaluate, which was [2], now has ID [1].
} (end loop)
So that's what I came up with, and it works like a charm. Sorry if my explanation is hard to understand, I'm trying to explain in a way that might make sense to both coders and Minecraft players, and maybe achieving neither :P

Two robots on a line

You probably know the problem with the two robots dropped on a line when you need to program them to meet.
Two robots are dropped from an airplane and land on a single line (with discrete positions) using a parachute which is left at the landing point. The robots are both facing north, they are an unknown distance apart, and one has landed directly east of the other.
The robots are now to be programmed such that they meet each other. They can be instructed to move left or right to a neighboring position and to check whether a parachute is present at the current location. If the other robot is met both robots stop there and live happily ever after.
The parachute check might conditionally execute any number of instructions and any block of instructions may be repeated unconditionally. Write down a program that both robots can follow simultaneously and which garuantees that they meet.
You have to create a generic algorithm (a little pleonastic) that applied to both robots guarantees that the robots will meet. They leave their parachute on the spot where they are dropped and they can check if in the current position there is a parachute.
The original statement is here: http://en.wikibooks.org/wiki/Puzzles/Logic_puzzles/Parachuted_Robots
There is also a solution that I don't understand. If someone can make any sense of it, please help me with a little explaning. Any other solution would be much appreciated.
My first thought on this problem would be to program the robot to choose randomly to first go right or left, and then make something like an exponential search: first go 2 positions to right, then 4 to left etc. If in one of this "trips" in right or left the robot finds the second parachute (the one that was used by the other robot), the robot will only search in that direction. Does this make any sense?
Thank you very much!
My program is actually shorter, and works like a charm too:
start: left
skipNext
goto start
next: left
goto next
This works because the second loop is faster than the first loop.
You can test your program here: http://david-peter.de/parachuting-robots/
Your "first thought" solution should work too, but it will take a while longer for the robots to meet than the solution you cited at wikibooks. To recap, the wikibooks solution is:
10 Go right
20 Go left
30 Go right
40 If Not Parachute GOTO 10
50 Go right
60 GOTO 50
In case you don't recognize the syntax, the author is trying to mimic BASIC, where the numbers 10-60 are line numbers, and the GOTOs are code jumps.
Lines 10-40 have both robots moving slowly right. The "right, left, right" steps slow down movement to the right. It could have just as easily been "right, wait". Line 40 checks for the parachute. When both robots landed on the line, exactly one of them was to the left of the other. The left robot will eventually find the other parachute. The right never will. When the left robot finds the right robot's parachute, it enters lines 50-60, where it moves right without the slowdown. Now that the left robot is moving right faster than the right robot, the left will eventually catch up.
Personally I think the algorithm you posed is more fun, since both robots would swing back and forth a lot. In a way it's a similar algorithm, but the slowdown grows linearly with each step.
It seems to me that your algorithm ought to work. The idea in the posted solution is that both robots keep a pattern of going right left right, meaning they are advancing right at a certain pace. But when the robot on the left finds the other's parachute, it starts moving to the right at a faster pace since it does not step once to the left as part of its walking pattern but keeps going right, eventually catching up to the robot on the right.
Both robots move left till the right robot finds the left robot's parachute and starts sprinting towards the left robot. Then they collide.
start: left
skipNext
goto start
goto moveLeftFast
moveLeftFast: left
goto moveLeftFast
I made this:
start: left
skipNext
goto start
fastL: left
left
goto fastL
The idea is simple: we go left one bit. One of the robots (the one on the right) will eventually bump into parachute and then it will skip out of the fist loop, and enter the second which makes him go left twice as fast.

Lights out game algorithm

It's a homework. I have to design and lights out game using backtracking description is below.
The game consists of a 5-by-5 grid of lights; when the game starts, a set of these lights (random, or one of a set of stored puzzle patterns) are switched on. Pressing one of the lights will toggle it, and the four lights adjacent to it, on and off. (Diagonal neighbours are not affected.) The game provides a puzzle: given some initial configuration where some lights are on and some are off, the goal is to switch all the lights off, preferably in
as few button presses as possible.
My approach is go from 1 to 25 and check if all the lights are off or not. If not then I will check for 1 to 24 and so on until I reach 1 or found solution. No if there is no solution then I will start from 2 to 24 and follow the above process till I reach 2 or found solution.
But through this I am not getting the result ? for example light at (0,0) (1,1) (2,2) (3,3) (4,4) are ON?
If any one need code I can post it.
Can any one tell me correct approach using backtracking to solve this game ?
Thanks.
There is a standard algorithm for solving this problem that is based on Gaussian elimination over GF(2). The idea is to set up a matrix representing the button presses a column vector representing the lights and then to use standard matrix simplification techniques to determine which buttons to press. It runs in polynomial time and does not require any backtracking.
I have an implementation of this algorithm that includes a mathematical description of how it works available on my personal site. I hope you find it useful!
Edit: If you are forced to use backtracking, you can use the following facts to do so:
Any solution will never push the same button twice, since doing so would cancel out a previous move.
Any solution either pushes the first button or does not.
Given this approach, you could solve this using backtracking using a simple recursive algorithm that keeps track of the current state of the board and which buttons you've already made decisions about:
If you've decided about each button, then return whether the board is solved or not.
Otherwise:
Try pushing the next button and seeing if the board is recursively solvable from there.
If so, return success.
Otherwise, try not pushing the next button and seeing if the board is recursively solvable from there.
If so, return success. If not, return failure.
This will explore a search space of size 225, which is about 32 million. That's big, but not insurmountably big.
Hope this helps!
Backtracking means:
Incrementally build a solution, throwing away impossible solutions.
Here is one approach using the fact that there is locality of inputs and outputs (pressing a button affects square around it).
problem = GIVEN
solutions = [[0],[1]] // array of binary matrix answers (two entries, a zero and a one)
for (problemSize = 1; problemSize <= 5; problemSize++) {
newSolutions = [];
foreach (solutions as oldSolution) {
candidateSolutions = arrayOfNByNMatriciesWithMatrixAtTopLeft(min(5,problemSize+1), oldSolution);
// size of candidateSolutions is 2^((problemSize+1)^2 - problemSize^2)
// except last round candidateSolutions == solutions
foreach (candidateSolutions as candidateSolution) {
candidateProblem = boardFromPressingButtonsInSolution(candidateSolution);
if (compareMatrix(problem, candidateProblem, 0, 0, problemSize, problemSize)==0)
newSolutions[] = candidateSolution;
}
}
solutions = newSolutions;
}
return solutions;
As already suggested, you should first form a set of simultaneous equations.
First thing to note is that a particular light button shall be pressed at most once because it does not make sense to toggle the set of lights twice.
Let Aij = Light ij Toggled { Aij = 0 or 1 }
There shall be 25 such variables.
Now for each of the lights, you can form an equation looking like
summation (Amn) = 0. { Amn = 5 light buttons that toggle the light mn }
So you will have 25 variables and 25 unknowns. You can solve these equations simultaneously.
If you need to solve it using backtracking or recursion you can solve the equations that way. Just assume an initial value of variables, see if they satisfy all the equations. If not, then back track.
The Naive Solution
First, you're going to need a way to represent the state of the board and a stack to store all of the states. At each step, make a copy of the board, changed to the new state. Compare that state to all states of the board you've encountered so far. If you haven't seen it, push that state on top of the stack and move on to the next move. If you have seen it, try the next move. Each level will have to try all possible 64 moves before popping the state from the stack (backtracking). You will want to use recursion to manage the state of the next move to check.
There are at most 264 possible board configurations, meaning you could potentially go on a very long chain of unique states and still run out of memory. (For reference, 1 GB is 230 bytes and you need a minimum of 8 bytes to store the board configuration) This algorithm is not likely to terminate in the lifetime of the known universe.
You need to do something clever to reduce your search space...
Greedy-First Search
You can do better by searching the states that are closest to the solved configuration first. At each step, sort the possible moves in order from most lights off to least lights off. Iterate in that order. This should work reasonably well but is not guaranteed to get the optimal solution.
Not All Lights-Out Puzzles Are Solvable
No matter what algorithm you use, there may not be a solution, meaning you might search forever (or several trillion years, at least) without finding a solution.
You will want to check the board for solvability (which is a much faster algorithm as it turns out) before wasting any time trying to find a solution.

How to simplify/optimize a 3d path?

I have a bunch of points in 3d ( an array that contains objects with x,y,z properties ).
My problem is that there are a lot of unnecessary points as illustrated in the image bellow:
(source: lifesine.eu)
How can I cleanup this path ?
At the moment the first thing that comes to mind is to
create an array for the optimized
path
loop though all the points starting
with index 1 instead of 0, and get
the 'direction' for the path. If the
direction changes, add the last of
the two points( the current, not the
previous ) to the optimized array.
The advantage is that the points are stored in a drawing order, so that makes them a path, not just random ( not sorted ) points.
Note: I am using actionscript 3, but I can understand syntax in other languages or pseudo code.
Thank you!
Check out Ramer-Douglas-Peucker algorithm
loop though all the points starting with index 1 instead of 0, and get the 'direction' for the path. If the direction changes, add the last of the two points( the current, not the previous ) to the optimized array.
If you think it's going to help, you should either think that the Earth is flat ;-)
Try this: if the path changes slightly, then skip every second point, thus finishing with twice as less points. If path changes appreciably, keep nodes as is. Then repeat with half of the threshold of what "slightly is (your lengths are doubled, so your sensitivity must increase) until you make no changes after a run.
I would go with your suggestion, but keep the current and previous point when the direction changes.
That way, you end up with the first and last point of each line segment.
I think your initial idea is great. I would add/change two things:
1) I would throw in a distance threshold into your algorithm: Only when the currently tested point is some minimum distance away from your last 'good' point, should you even test it. Depending on the source of your path data (a magnetic tracker perhaps?), stationarity may not be reflected well in your raw data, due to measurement noise. This might lead to relatively large directional changes in a very small area that are essentially meaningless.
2) When you detect a large enough change, do not add the currently tested point (as you suggested), but the previous one. Otherwise you may end up misrepresenting the path. An example (in 2D): the path consisting of (0,0)->(1,0)->(2,0)->(3,0)->(4,0)->(5,5) would end up as (0,0)->(5,5) using your methods, which I wouldn't consider a good representation of the path. Better would be (0, 0)->(4,0)->(5,5).

Mahjong - Arrange tiles to ensure at least one path to victory, regardless of layout

Regardless of the layout being used for the tiles, is there any good way to divvy out the tiles so that you can guarantee the user that, at the beginning of the game, there exists at least one path to completing the puzzle and winning the game?
Obviously, depending on the user's moves, they can cut themselves off from winning. I just want to be able to always tell the user that the puzzle is winnable if they play well.
If you randomly place tiles at the beginning of the game, it's possible that the user could make a few moves and not be able to do any more. The knowledge that a puzzle is at least solvable should make it more fun to play.
Place all the tiles in reverse (ie layout out the board starting in the middle, working out)
To tease the player further, you could do it visibly but at very high speed.
Play the game in reverse.
Randomly lay out pieces pair by pair, in places where you could slide them into the heap. You'll need a way to know where you're allowed to place pieces in order to end up with a heap that matches some preset pattern, but you'd need that anyway.
I know this is an old question, but I came across this when solving the problem myself. None of the answers here are quite perfect, and several of them have complicated caveats or will break on pathological layouts. Here is my solution:
Solve the board (forward, not backward) with unmarked tiles. Remove two free tiles at a time. Push each pair you remove onto a "matched pair" stack. Often, this is all you need to do.
If you run into a dead end (numFreeTiles == 1), just reset your generator :) I have found I usually don't hit dead ends, and have so far have a max retry count of 3 for the 10-or-so layouts I have tried. Once I hit 8 retries, I give up and just randomly assign the rest of the tiles. This allows me to use the same generator for both setting up the board, and the shuffle feature, even if the player screwed up and made a 100% unsolvable state.
Another solution when you hit a dead end is to back out (pop off the stack, replacing tiles on the board) until you can take a different path. Take a different path by making sure you match pairs that will remove the original blocking tile.
Unfortunately, depending on the board, this may loop forever. If you end up removing a pair that resembles a "no outlet" road, where all subsequent "roads" are a dead end, and there are multiple dead ends, your algorithm will never complete. I don't know if it is possible to design a board where this would be the case, but if so, there is still a solution.
To solve that bigger problem, treat each possible board state as a node in a DAG, with each selected pair being an edge on that graph. Do a random traversal, until you find a leaf node at depth 72. Keep track of your traversal history so that you never repeat a descent.
Since dead ends are more rare than first-try solutions in the layouts I have used, what immediately comes to mind is a hybrid solution. First try to solve it with minimal memory (store selected pairs on your stack). Once you've hit the first dead end, degrade to doing full marking/edge generation when visiting each node (lazy evaluation where possible).
I've done very little study of graph theory, though, so maybe there's a better solution to the DAG random traversal/search problem :)
Edit: You actually could use any of my solutions w/ generating the board in reverse, ala the Oct 13th 2008 post. You still have the same caveats, because you can still end up with dead ends. Generating a board in reverse has more complicated rules, though. E.g, you are guaranteed to fail your setup if you don't start at least SOME of your rows w/ the first piece in the middle, such as in a layout w/ 1 long row. Picking a completely random (legal) first move in a forward-solving generator is more likely to lead to a solvable board.
The only thing I've been able to come up with is to place the tiles down in matching pairs as kind of a reverse Mahjong Solitaire game. So, at any point during the tile placement, the board should look like it's in the middle of a real game (ie no tiles floating 3 layers up above other tiles).
If the tiles are place in matching pairs in a reverse game, it should always result in at least one forward path to solve the game.
I'd love to hear other ideas.
I believe the best answer has already been pushed up: creating a set by solving it "in reverse" - i.e. starting with a blank board, then adding a pair somewhere, add another pair in a solvable position, and so on...
If you a prefer "Big Bang" approach (generating the whole set randomly at the beginning), are a very macho developer or just feel masochistic today, you could represent all the pairs you can take out from the given set and how they depend on each other via a directed graph.
From there, you'd only have to get the transitive closure of that set and determine if there's at least one path from at least one of the initial legal pairs that leads to the desired end (no tile pairs left).
Implementing this solution is left as an exercise to the reader :D
Here are rules i used in my implementation.
When buildingheap, for each fret in a pair separately, find a cells (places), which are:
has all cells at lower levels already filled
place for second fret does not block first, considering if first fret already put onboard
both places are "at edges" of already built heap:
EITHER has at least one neighbour at left or right side
OR it is first fret in a row (all cells at right and left are recursively free)
These rules does not guarantee a build will always successful - it sometimes leave last 2 free cells self-blocking, and build should be retried (or at least last few frets)
In practice, "turtle" built in no more then 6 retries.
Most of existed games seems to restrict putting first ("first on row") frets somewhere in a middle. This come up with more convenient configurations, when there are no frets at edges of very long rows, staying up until last player moves. However, "middle" is different for different configurations.
Good luck :)
P.S.
If you've found algo that build solvable heap in one turn - please let me know.
You have 144 tiles in the game, each of the 144 tiles has a block list..
(top tile on stack has an empty block list)
All valid moves require that their "current__vertical_Block_list" be empty.. this can be a 144x144 matrix so 20k of memory plus a LEFT and RIGHT block list, also 20 k each.
Generate a valid move table from (remaning_tiles) AND ((empty CURRENT VERTICAL BLOCK LIST) and ((empty CURRENT LEFT BLOCK LIST) OR (empty CURRENT RIGHT BLOCK LIST)))
Pick 2 random tiles from the valid move table, record them
Update the (current tables Vert, left and right), record the Tiles removed to a stack
Now we have a list of moves that constitute a valid game. Assign matching tile types to each of the 72 moves.
for challenging games, track when each tile becomes available. find sets that have are (early early early late) and (late late late early) since it's blank, you find 1 EE 1 LL and 2 LE blocks.. of the 2 LE block, find an EARLY that blocks ANY other EARLY that (except rightblocking a left side piece)
Once youve got a valid game play around with the ordering.
Solitaire? Just a guess, but I would assume that your computer would need to beat the game(or close to it) to determine this.
Another option might be to have several preset layouts(that allow winning, mixed in with your current level.
To some degree you could try making sure that one of the 4 tiles is no more than X layers below another X.
Most games I see have the shuffle command for when someone gets stuck.
I would try a mix of things and see what works best.

Resources