Skip to content

Instantly share code, notes, and snippets.

@Ludo6431
Last active December 28, 2015 06:09
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save Ludo6431/7454809 to your computer and use it in GitHub Desktop.
Save Ludo6431/7454809 to your computer and use it in GitHub Desktop.
"Cheap" answer to https://plus.google.com/100596916576106169058/posts/W87V4uTsASn (older versions of the gist refers to this problem: https://plus.google.com/100596916576106169058/posts/SAae56Bo8GZ) Uses recursivity :/
// Ludovic Lacoste <ludolacost@gmail.com>
#include <stdlib.h>
#include <stdio.h>
#include <stdint.h>
#include <assert.h>
// #### definitions ####
typedef enum{
E_DUCK_YELLOW,
E_DUCK_GREEN,
NUM_E_DUCK
} eDuck;
typedef enum{
E_BOX_1,
E_BOX_2,
E_BOX_3,
E_BOX_4,
E_BOX_5,
E_BOX_6,
E_BOX_7,
E_BOX_8,
E_BOX_9,
E_BOX_10,
E_BOX_11,
E_BOX_12,
E_BOX_13,
NUM_E_BOX
} eBox;
typedef enum{
E_COL_BLUE,
E_COL_RED,
NUM_E_COL
} eCol;
typedef struct _sState sState;
struct _sState{
int dist;
struct _sState *prev; // best (minimal dist to start) previous state
};
sState st[NUM_E_BOX][NUM_E_BOX] = {{0}};
#define BOX_YELLOW(p) (((p) - &st[0][0])/NUM_E_BOX)
#define BOX_GREEN(p) (((p) - &st[0][0])%NUM_E_BOX)
eCol col[NUM_E_BOX] = {
E_COL_RED,
E_COL_RED,
E_COL_RED,
E_COL_RED,
E_COL_BLUE,
E_COL_RED,
E_COL_BLUE,
E_COL_RED,
E_COL_BLUE,
E_COL_RED,
E_COL_BLUE,
E_COL_BLUE,
E_COL_RED};
eBox next[NUM_E_COL][NUM_E_BOX] = {
// other duck on blue box
{
// I am on box 1,2,3,4,5,..., I can go to:
E_BOX_2,
E_BOX_4,
E_BOX_5,
E_BOX_1,
E_BOX_10,
E_BOX_1,
E_BOX_12,
E_BOX_3,
E_BOX_7,
E_BOX_11,
E_BOX_9,
E_BOX_11,
E_BOX_3
},
// other duck on red box
{
// I am on box 1,2,3,4,5,..., I can go to:
E_BOX_5,
E_BOX_8,
E_BOX_2,
E_BOX_9,
E_BOX_7,
E_BOX_12,
E_BOX_4,
E_BOX_10,
E_BOX_6,
E_BOX_13,
E_BOX_6,
E_BOX_13,
E_BOX_8
}
};
sState *start = &st[E_BOX_10][E_BOX_11];
sState *end = &st[E_BOX_4][E_BOX_4];
void print_solution(sState *curr){
if(!curr)
return;
do{
printf("\t%i - y%li/g%li%s\n", curr->dist-1, BOX_YELLOW(curr)+1, BOX_GREEN(curr)+1, curr==start?" start":curr==end?" end":"");
curr = curr->prev;
}while(curr);
}
void step(int dist, sState *curr){
sState *new_st;
eBox new_box;
dist++;
curr->dist = dist;
if(curr == end){
// found one solution
return;
}
// try to move yellow ducky
new_box = next[col[BOX_GREEN(curr)]][BOX_YELLOW(curr)];
new_st = &st[new_box][BOX_GREEN(curr)];
if(new_st != start && ((!new_st->prev) || (new_st->dist > dist))){
new_st->prev = curr;
step(dist, new_st);
if(BOX_YELLOW(curr) == BOX_GREEN(curr)){
return;
}
}
// try to move green ducky
new_box = next[col[BOX_YELLOW(curr)]][BOX_GREEN(curr)];
new_st = &st[BOX_YELLOW(curr)][new_box];
if(new_st != start && ((!new_st->prev) || (new_st->dist > dist))){
new_st->prev = curr;
step(dist, new_st);
}
}
// #### entry point ####
int main(){
// init
int i, j, ret;
assert(BOX_YELLOW(start) == E_BOX_10);
assert(BOX_GREEN(start) == E_BOX_11);
step(0, start);
printf("one of the shortest solutions (%i steps):\n", end->dist-1);
print_solution(end);
return EXIT_SUCCESS;
}
one of the shortest solutions (34 steps):
34 - y4/g4 end
33 - y4/g7
32 - y2/g7
31 - y1/g7
30 - y6/g7
29 - y6/g5
28 - y6/g1
27 - y9/g1
26 - y9/g4
25 - y9/g2
24 - y4/g2
23 - y4/g3
22 - y7/g3
21 - y5/g3
20 - y5/g13
19 - y1/g13
18 - y1/g12
17 - y4/g12
16 - y2/g12
15 - y2/g6
14 - y3/g6
13 - y3/g9
12 - y13/g9
11 - y13/g4
10 - y10/g4
9 - y10/g7
8 - y5/g7
7 - y5/g9
6 - y5/g11
5 - y5/g12
4 - y3/g12
3 - y13/g12
2 - y13/g6
1 - y10/g6
0 - y10/g11 start
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment