day23: delete dead code, rename structs/macros, use native rand()
This commit is contained in:
@@ -21,70 +21,55 @@
|
||||
#include "bits.h"
|
||||
#include "list.h"
|
||||
|
||||
typedef enum {
|
||||
A, B, C, D
|
||||
} amphipod_t;
|
||||
|
||||
static const u64 cost[] = {
|
||||
static const u32 cost[] = {
|
||||
1, 10, 100, 1000
|
||||
};
|
||||
|
||||
#define _ROOM_A 0x00000F00 /* 000000000000111100000000*/
|
||||
#define _ROOM_B 0x0000F000 /* 000000001111000000000000*/
|
||||
#define _ROOM_C 0x000F0000 /* 000011110000000000000000*/
|
||||
#define _ROOM_D 0x00F00000 /* 111100000000000000000000*/
|
||||
#define _ROOM 0x00FFFF00 /* 111111111111111100000000 */
|
||||
#define _HALLWAY 0x0000007F /* 000000000000000001111111 */
|
||||
#define ROOM_A 0x00000F00 /* 000000000000111100000000 */
|
||||
#define ROOM_B 0x0000F000 /* 000000001111000000000000 */
|
||||
#define ROOM_C 0x000F0000 /* 000011110000000000000000 */
|
||||
#define ROOM_D 0x00F00000 /* 111100000000000000000000 */
|
||||
#define ROOMS 0x00FFFF00 /* 111111111111111100000000 */
|
||||
#define HALLWAY 0x0000007F /* 000000000000000001111111 */
|
||||
|
||||
#define BIT(c) (1 << (c))
|
||||
|
||||
#define RAND_SEED 1337 /* seed for random generator */
|
||||
|
||||
static u32 rooms[4] = { _ROOM_A, _ROOM_B, _ROOM_C, _ROOM_D };
|
||||
static u64 result = -1;
|
||||
static u32 rooms[4] = { ROOM_A, ROOM_B, ROOM_C, ROOM_D };
|
||||
static u32 result = -1;
|
||||
|
||||
/* full position description
|
||||
*/
|
||||
typedef struct pos {
|
||||
u32 amp[4]; /* bitmask of amphipods position */
|
||||
u32 amp[4]; /* bitmask of amphipods positions */
|
||||
u32 occupied; /* bitmask for all occupied cells */
|
||||
u32 final; /* bitmask for correct position */
|
||||
u64 zobrist; /* for zobrist_2() */
|
||||
u64 cost; /* cost till this position */
|
||||
struct list_head list; /* */
|
||||
u32 zobrist; /* for zobrist_2() */
|
||||
u32 cost; /* cost till this position */
|
||||
struct list_head list; /* positions list */
|
||||
} pos_t;
|
||||
|
||||
/* zobrist hash used to ignore positions already seen
|
||||
*/
|
||||
typedef struct hash {
|
||||
u64 zobrist; /* zobrist hash */
|
||||
u32 amp[4];
|
||||
u64 cost;
|
||||
struct list_head list;
|
||||
u32 zobrist; /* zobrist hash */
|
||||
u32 amp[4]; /* bitmask of amphipods positions */
|
||||
u32 cost; /* cost for this hash */
|
||||
struct list_head list; /* collision list */
|
||||
} hash_t;
|
||||
|
||||
#define HASH_SIZE 131071
|
||||
#define HASH_SEEN (HASH_SIZE + 1)
|
||||
//#define HASH_SIZE 131072
|
||||
#define HASH_SIZE 65536
|
||||
|
||||
struct {
|
||||
u32 count;
|
||||
struct list_head list;
|
||||
} hasht[HASH_SIZE];
|
||||
|
||||
static inline u32 get_occupancy(pos_t *pos)
|
||||
{
|
||||
return pos->amp[A] | pos->amp[B] | pos->amp[C] | pos->amp[D];
|
||||
}
|
||||
struct list_head hasht[HASH_SIZE];
|
||||
|
||||
pool_t *pool_pos;
|
||||
pool_t *pool_hash;
|
||||
|
||||
LIST_HEAD(pos_queue);
|
||||
|
||||
static u64 zobrist_table[24][4];
|
||||
|
||||
/* from https://stackoverflow.com/a/33021408/3079831
|
||||
*/
|
||||
#define IMAX_BITS(m) ((m)/((m)%255+1) / 255%255*8 + 7-86/((m)%255+12))
|
||||
#define RAND_MAX_WIDTH IMAX_BITS(RAND_MAX)
|
||||
_Static_assert((RAND_MAX & (RAND_MAX + 1u)) == 0, "RAND_MAX not a Mersenne number");
|
||||
|
||||
static u32 zobrist_table[24][4];
|
||||
|
||||
/*
|
||||
* #############
|
||||
@@ -98,111 +83,38 @@ _Static_assert((RAND_MAX & (RAND_MAX + 1u)) == 0, "RAND_MAX not a Mersenne numbe
|
||||
* We name a-g H1-H7, h & l are A1-A2, i & m are B1 & B2, etc...
|
||||
*/
|
||||
|
||||
/* note that to determine of hallway space is left or right,
|
||||
/* note that to determine if hallway space is left or right,
|
||||
* we simply need to divide the room number by 4.
|
||||
* Example: Room C cells are 16-19.
|
||||
* We have: 16 / 4 = 16 >> 2 = 4, and 19 / 4 = 19 >> 2 = 4, meaning
|
||||
* that H1 (0), H2 (1), H3 (2), H4 (3) are left.
|
||||
*/
|
||||
typedef enum {
|
||||
_H1 = 0, _H2, _H3, _H4, _H5, _H6, _H7, /* 0-6 */
|
||||
_WRONG = 7, /* 7 */
|
||||
_A1 = 8, _A2, _A3, _A4, /* 8-11 */
|
||||
_B1, _B2, _B3, _B4, /* 12-15 */
|
||||
_C1, _C2, _C3, _C4, /* 16-19 */
|
||||
_D1, _D2, _D3, _D4, /* 20-23 */
|
||||
} _space_t;
|
||||
enum squares {
|
||||
H1 = 0, H2, H3, H4, H5, H6, H7 = 6, /* 0-6 */
|
||||
A1 = 8, A2, A3, A4, /* 8-11 */
|
||||
B1, B2, B3, B4, /* 12-15 */
|
||||
C1, C2, C3, C4, /* 16-19 */
|
||||
D1, D2, D3, D4, /* 20-23 */
|
||||
};
|
||||
|
||||
#define HALLWAY(b) ((b) & _HALLWAY)
|
||||
#define ROOM(b) ((b) & _ROOM)
|
||||
|
||||
#define IN_HALLWAY(c) ((int)(c) >= _H1 && (int)(c) <= _H7)
|
||||
#define IN_ROOM(c) (((int)(c) >= _A1 && (int)(c) <= _A4) || \
|
||||
((int)(c) >= _B1 && (int)(c) <= _B4) || \
|
||||
((int)(c) >= _C1 && (int)(c) <= _C4) || \
|
||||
((int)(c) >= _D1 && (int)(c) <= _D4))
|
||||
|
||||
#define LEFT 0
|
||||
#define LEFT 0
|
||||
#define RIGHT 1
|
||||
|
||||
static s32 room_exit[4][2][6] = {
|
||||
{ { _H2, _H1, -1 }, /* room A left */
|
||||
{ _H3, _H4, _H5, _H6, _H7, -1 } /* room A right */
|
||||
},
|
||||
{ { _H3, _H2, _H1, -1 }, /* room B left */
|
||||
{ _H4, _H5, _H6, _H7, -1 } /* room B right */
|
||||
},
|
||||
{ { _H4, _H3, _H2, _H1, -1 }, /* room C left */
|
||||
{ _H5, _H6, _H7, -1 } /* room C right */
|
||||
},
|
||||
{ { _H5, _H4, _H3, _H2, _H1, -1 }, /* room D left */
|
||||
{ _H6, _H7, -1 } /* room D right */
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
char *cells[] = {
|
||||
"H1", "H2", "H3", "H4", "H5", "H6", "H7", "BAD",
|
||||
"A1", "A2", "A3", "A4",
|
||||
"B1", "B2", "B3", "B4",
|
||||
"C1", "C2", "C3", "C4",
|
||||
"D1", "D2", "D3", "D4",
|
||||
};
|
||||
|
||||
typedef enum {
|
||||
H1 = BIT(_H1), H2 = BIT(_H2), H3 = (_H3), H4 = (_H4),
|
||||
H5 = (_H5), H6 = (_H6), H7 = (_H7),
|
||||
A1 = (_A1), A2 = (_A2), A3 = (_A3), A4 = (_A4),
|
||||
B1 = (_B1), B2 = (_B2), B3 = (_B3), B4 = (_B4),
|
||||
C1 = (_C1), C2 = (_C2), C3 = (_C3), C4 = (_C4),
|
||||
D1 = (_D1), D2 = (_D2), D3 = (_D3), D4 = (_D4),
|
||||
} space_t;
|
||||
|
||||
/* Steps to move to hallway
|
||||
/**
|
||||
* set bits between 2 positions, excluding MSB one:
|
||||
* setbits(2, 4) -> 0001100
|
||||
* pos: 4 2
|
||||
*/
|
||||
typedef enum {
|
||||
A1H = 1, A2H = 2, A3H = 3, A4H = 4
|
||||
} out_t;
|
||||
#define setbits(i, j) (((1 << ((j) - (i))) - 1) << (i))
|
||||
|
||||
/* Mask which disallow moves to hallway
|
||||
/* distance between position over rooms to other hallway positions.
|
||||
*/
|
||||
typedef struct {
|
||||
uint mask, dist;
|
||||
} possible_move_t;
|
||||
|
||||
/* Steps to move from space outside room to hallway destination
|
||||
*/
|
||||
typedef enum {
|
||||
AH1 = 2, AH2 = 1, AH3 = 1, AH4 = 3, AH5 = 5, AH6 = 7 , AH7 = 8,
|
||||
BH1 = 4, BH2 = 3, BH3 = 1, BH4 = 1, BH5 = 3, BH6 = 5 , BH7 = 6,
|
||||
CH1 = 6, CH2 = 5, CH3 = 3, CH4 = 1, CH5 = 1, CH6 = 3 , CH7 = 4,
|
||||
DH1 = 8, DH2 = 7, DH3 = 5, DH4 = 3, DH5 = 1, DH6 = 1 , DH7 = 2
|
||||
} steps_t;
|
||||
|
||||
/*
|
||||
* #############
|
||||
* #ab.c.d.e.fg#
|
||||
* ###h#i#j#k###
|
||||
* #l#m#n#o#
|
||||
* #p#q#r#s#
|
||||
* #t#u#v#w#
|
||||
* #########
|
||||
*/
|
||||
|
||||
/* set bits between 2 positions
|
||||
* setbits(2, 4) -> 0011100
|
||||
*/
|
||||
static u32 setbits(int from, int to)
|
||||
{
|
||||
u32 ret = 0;
|
||||
for (int i = from; i < to; ++i)
|
||||
ret |= BIT(i);
|
||||
log_f(4, "(%d, %d) = %d\n", from, to, ret);
|
||||
return ret;
|
||||
}
|
||||
|
||||
static int h2h[][7] = {
|
||||
{ 2, 1, 1, 3, 5, 7, 8 }, /* A */
|
||||
{ 4, 3, 1, 1, 3, 5, 6 }, /* B */
|
||||
{ 6, 5, 3, 1, 1, 3, 4 }, /* C */
|
||||
{ 8, 7, 5, 3, 1, 1, 2 } /* D */
|
||||
/* H1 H2 H3 H4 H5 H6 H7 */
|
||||
{ 2, 1, 1, 3, 5, 7, 8 }, /* from virtual cell on top of A */
|
||||
{ 4, 3, 1, 1, 3, 5, 6 }, /* B */
|
||||
{ 6, 5, 3, 1, 1, 3, 4 }, /* C */
|
||||
{ 8, 7, 5, 3, 1, 1, 2 } /* D */
|
||||
};
|
||||
|
||||
/* get a position from memory pool
|
||||
@@ -237,11 +149,8 @@ static void free_pos(pos_t *pos)
|
||||
*/
|
||||
static void push_pos(pos_t *pos)
|
||||
{
|
||||
if (pos) {
|
||||
if (pos)
|
||||
list_add(&pos->list, &pos_queue);
|
||||
} else {
|
||||
exit(1);
|
||||
}
|
||||
}
|
||||
|
||||
/* pop a position from stack
|
||||
@@ -255,61 +164,44 @@ static pos_t *pop_pos()
|
||||
return pos;
|
||||
}
|
||||
|
||||
static u64 rand64(void) {
|
||||
u64 r = 0;
|
||||
for (int i = 0; i < 64; i += RAND_MAX_WIDTH) {
|
||||
r <<= RAND_MAX_WIDTH;
|
||||
r ^= (unsigned) rand();
|
||||
}
|
||||
return r;
|
||||
}
|
||||
|
||||
static void zobrist_init()
|
||||
{
|
||||
log_f(1, "seed=%d rand_max=%d\n", RAND_SEED, RAND_MAX);
|
||||
srand(RAND_SEED);
|
||||
for (int i = 0; i < 24; ++i) {
|
||||
for (int j = 0; j < 4; ++j) {
|
||||
zobrist_table[i][j] = rand64();
|
||||
zobrist_table[i][j] = rand();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static inline u64 zobrist_1(pos_t *pos)
|
||||
static inline u32 zobrist_1(pos_t *pos)
|
||||
{
|
||||
u32 tmp;
|
||||
int bit;
|
||||
u64 zobrist = 0;
|
||||
u32 zobrist = 0;
|
||||
|
||||
for (int amp = 0; amp < 4; ++amp) {
|
||||
bit_for_each32_2(bit, tmp, pos->amp[amp]) {
|
||||
//log_f(2, "amp=%d/%c bit=%d\n", amp, amp+'A', bit);
|
||||
zobrist ^= zobrist_table[bit][amp];
|
||||
}
|
||||
}
|
||||
log_f(1, "zobrist=%lu -> %lu\n", zobrist, zobrist % HASH_SIZE);
|
||||
return zobrist;
|
||||
}
|
||||
|
||||
/* calculate zobrist hash from previous zobrist value
|
||||
*/
|
||||
static inline u64 zobrist_2(pos_t *pos, int amp, u32 from, u32 to)
|
||||
static inline u32 zobrist_2(pos_t *pos, int amp, u32 from, u32 to)
|
||||
{
|
||||
u64 zobrist = pos->zobrist;
|
||||
u32 zobrist = pos->zobrist;
|
||||
|
||||
zobrist ^= zobrist_table[from][amp];
|
||||
zobrist ^= zobrist_table[to][amp];
|
||||
log_f(1, "zobrist(%d, %u, %u)=%lu -> %lu (amp=%d from=%u to=%u)\n",
|
||||
amp, from, to, zobrist, zobrist % HASH_SIZE, amp, from, to);
|
||||
return zobrist;
|
||||
}
|
||||
|
||||
static void hash_init()
|
||||
{
|
||||
for (int i = 0; i < HASH_SIZE; ++i) {
|
||||
hasht[i].count = 0;
|
||||
INIT_LIST_HEAD(&hasht[i].list);
|
||||
}
|
||||
for (int i = 0; i < HASH_SIZE; ++i)
|
||||
INIT_LIST_HEAD(&hasht[i]);
|
||||
}
|
||||
|
||||
/* get a position from memory pool
|
||||
@@ -331,11 +223,10 @@ static hash_t *get_hash(pos_t *pos)
|
||||
static hash_t *hash(pos_t *pos)
|
||||
{
|
||||
hash_t *cur;
|
||||
u32 hashpos;
|
||||
u64 zobrist = pos->zobrist;
|
||||
u32 hashpos, zobrist = pos->zobrist;
|
||||
|
||||
hashpos = zobrist % HASH_SIZE;
|
||||
list_for_each_entry(cur, &hasht[hashpos].list, list) {
|
||||
list_for_each_entry(cur, &hasht[hashpos], list) {
|
||||
if (zobrist == cur->zobrist) {
|
||||
if (pos->amp[0] == cur->amp[0] &&
|
||||
pos->amp[1] == cur->amp[1] &&
|
||||
@@ -346,35 +237,55 @@ static hash_t *hash(pos_t *pos)
|
||||
}
|
||||
}
|
||||
}
|
||||
hasht[hashpos].count++;
|
||||
cur = get_hash(pos);
|
||||
|
||||
list_add(&cur->list, &hasht[hashpos].list);
|
||||
list_add(&cur->list, &hasht[hashpos]);
|
||||
return cur;
|
||||
}
|
||||
|
||||
|
||||
/* generate possible moves between hallway and rooms
|
||||
/* Next table shows the hallway possible moves from rooms, nearest to farthest.
|
||||
* When generating moves, this allows to stop one direction as soon as move
|
||||
* is impossible.
|
||||
* Example: Moving right from room C, if H6 is occupied, we won't try to
|
||||
* evaluate a move on H7.
|
||||
*/
|
||||
static int room_exit[4][2][6] = {
|
||||
{ { H2, H1, -1 }, /* room A left */
|
||||
{ H3, H4, H5, H6, H7, -1 } }, /* right */
|
||||
{ { H3, H2, H1, -1 }, /* room B left */
|
||||
{ H4, H5, H6, H7, -1 } }, /* right */
|
||||
{ { H4, H3, H2, H1, -1 }, /* room C left */
|
||||
{ H5, H6, H7, -1 } }, /* right */
|
||||
{ { H5, H4, H3, H2, H1, -1 }, /* room D left */
|
||||
{ H6, H7, -1 } } /* right */
|
||||
};
|
||||
|
||||
/* Mask which disallow moves to hallway
|
||||
*/
|
||||
typedef struct {
|
||||
uint mask;
|
||||
uint dist;
|
||||
} possible_move_t;
|
||||
|
||||
static possible_move_t moves[24][24];
|
||||
|
||||
/* calculate distance and move mask for all possible moves
|
||||
* (room -> hallway ans hallway -> room)
|
||||
/* Generate all possible moves and moves masks
|
||||
* (rooms -> hallway and hallway -> rooms)
|
||||
*/
|
||||
static possible_move_t (*init_moves())[24]
|
||||
static void init_moves(void)
|
||||
{
|
||||
int hallway, room, dist, pos;
|
||||
u32 mask_h, mask_r;
|
||||
|
||||
for (room = _A1; room <= _D4; ++room) {
|
||||
for (room = A1; room <= D4; ++room) {
|
||||
pos = (room >> 2) - 2;
|
||||
for (hallway = _H1; hallway <= _H7; ++hallway) {
|
||||
for (hallway = H1; hallway <= H7; ++hallway) {
|
||||
dist = h2h[pos][hallway] + room % 4 + 1;
|
||||
|
||||
/* from room to hallway */
|
||||
if (room >> 2 > hallway)
|
||||
if (room >> 2 > hallway) /* left */
|
||||
mask_h = setbits(hallway, room >> 2);
|
||||
else
|
||||
else /* right */
|
||||
mask_h = setbits(room >> 2, hallway + 1);
|
||||
mask_r = setbits(room & ~3, room);
|
||||
moves[room][hallway].mask = mask_r | mask_h;
|
||||
@@ -388,19 +299,15 @@ static possible_move_t (*init_moves())[24]
|
||||
mask_r = setbits(room & ~3, room + 1);
|
||||
moves[hallway][room].mask = mask_r | mask_h;
|
||||
moves[hallway][room].dist = dist;
|
||||
|
||||
}
|
||||
log(3, "\n");
|
||||
}
|
||||
return moves;
|
||||
}
|
||||
|
||||
|
||||
static pos_t *newmove(pos_t *pos, amphipod_t amp, u32 from, u32 to)
|
||||
static pos_t *newmove(pos_t *pos, int amp, u32 from, u32 to)
|
||||
{
|
||||
pos_t *newpos;
|
||||
int rows = popcount32(pos->amp[0]);
|
||||
possible_move_t *move = &moves[from][to];
|
||||
pos_t *newpos;
|
||||
u32 bit_from = BIT(from), bit_to = BIT(to);
|
||||
|
||||
if (pos->cost + move->dist * cost[amp] >= result)
|
||||
@@ -414,15 +321,14 @@ static pos_t *newmove(pos_t *pos, amphipod_t amp, u32 from, u32 to)
|
||||
newpos->occupied |= bit_to;
|
||||
newpos->cost += move->dist * cost[amp];
|
||||
|
||||
if (HALLWAY(bit_from)) { /* from hallway */
|
||||
newpos->final |= BIT(to);
|
||||
if (bit_to & ROOMS) { /* to room => final position */
|
||||
newpos->final |= bit_to;
|
||||
if (popcount32(newpos->final) == rows * 4) {
|
||||
if (newpos->cost < result)
|
||||
result = newpos->cost;
|
||||
free_pos(newpos);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
newpos->zobrist = zobrist_2(newpos, amp, from, to);
|
||||
@@ -439,25 +345,23 @@ static pos_t *newmove(pos_t *pos, amphipod_t amp, u32 from, u32 to)
|
||||
*/
|
||||
static void genmoves(pos_t *pos)
|
||||
{
|
||||
amphipod_t amp;
|
||||
int amp, cell, rows = popcount32(pos->amp[0]);
|
||||
u32 tmp;
|
||||
int bit;
|
||||
int rows = popcount32(pos->amp[0]);
|
||||
|
||||
for (amp = A; amp <= D; ++amp) {
|
||||
u32 cur = pos->amp[amp];
|
||||
bit_for_each32_2(bit, tmp, cur) {
|
||||
if (bit >= _A1) { /* in a room */
|
||||
if (BIT(bit) & pos->final)
|
||||
for (amp = 0; amp < 4; ++amp) {
|
||||
u32 cur_amp = pos->amp[amp];
|
||||
bit_for_each32_2(cell, tmp, cur_amp) {
|
||||
if (cell >= A1) { /* in a room */
|
||||
if (BIT(cell) & pos->final)
|
||||
continue;
|
||||
int room = (bit >> 2) - 2;
|
||||
int room = (cell >> 2) - 2;
|
||||
for (int side = LEFT; side <= RIGHT; ++side) {
|
||||
int *d = room_exit[room][side];
|
||||
for (; *d != -1; ++d) {
|
||||
possible_move_t *move = &moves[bit][*d];
|
||||
possible_move_t *move = &moves[cell][*d];
|
||||
if (move->mask & pos->occupied)
|
||||
break;
|
||||
newmove(pos, amp, bit, *d);
|
||||
newmove(pos, amp, cell, *d);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -472,7 +376,7 @@ static void genmoves(pos_t *pos)
|
||||
if ((room & pos->final) != (room & pos->occupied))
|
||||
continue;
|
||||
bit_for_each32_2(dest, tmp, room) {
|
||||
possible_move_t *move = &moves[bit][dest];
|
||||
possible_move_t *move = &moves[cell][dest];
|
||||
if (move->mask & pos->occupied)
|
||||
break;
|
||||
found = dest;
|
||||
@@ -480,7 +384,7 @@ static void genmoves(pos_t *pos)
|
||||
break;
|
||||
}
|
||||
if (found)
|
||||
newmove(pos, amp, bit, found);
|
||||
newmove(pos, amp, cell, found);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -503,7 +407,6 @@ static pos_t *read_input(int part)
|
||||
|
||||
while ((buflen = getline(&buf, &alloc, stdin)) > 0) {
|
||||
buf[--buflen] = 0;
|
||||
log(1, "line=%d str=%s\n", line, buf);
|
||||
if (line == 2 || line == 3) {
|
||||
|
||||
if (part == 2 && line == 3) {
|
||||
@@ -528,7 +431,7 @@ static pos_t *read_input(int part)
|
||||
line++;
|
||||
adjline++;
|
||||
}
|
||||
pos->occupied = get_occupancy(pos);
|
||||
pos->occupied = pos->amp[0] | pos->amp[1] | pos->amp[2] | pos->amp[3];
|
||||
/* check if some amphipods are already in correct place
|
||||
*/
|
||||
for (int room = 0; room < 4; ++room) {
|
||||
@@ -581,6 +484,8 @@ int main(int ac, char **av)
|
||||
pool_pos = pool_create("pos", 1024, sizeof(pos_t));
|
||||
pool_hash = pool_create("hash", 1024, sizeof(hash_t));
|
||||
|
||||
//printf("b1 = %d\n", setbits(2, 4));
|
||||
//printf("b2 = %d\n", setbits(2, 4));
|
||||
zobrist_init();
|
||||
hash_init();
|
||||
init_moves();
|
||||
@@ -593,6 +498,6 @@ int main(int ac, char **av)
|
||||
free_pos(pos);
|
||||
}
|
||||
|
||||
printf("%s : res=%ld\n", *av, result);
|
||||
printf("%s : res=%d\n", *av, result);
|
||||
exit(0);
|
||||
}
|
||||
|
Reference in New Issue
Block a user