#pragma once #include "Effect.h" #include "prototypes.h" #define SNAKE_DIR_NORTH 0 #define SNAKE_DIR_EAST 1 #define SNAKE_DIR_SOUTH 2 #define SNAKE_DIR_WEST 3 #define SNAKE_DEBUG false class SnakeEffect : public Effect { private: Coords _pos; Coords _apple; int8_t _dir = SNAKE_DIR_NORTH; uint8_t* _map; uint16_t _pixels; uint8_t _length; unsigned long _last_apple_at; unsigned long _last_move_at; uint16_t _round; // Neural net config // These are actually float values. But in order to prevent rounding errors and stuff, they are provided // in form of the raw binary data of the IEE754 floating point numbers. // In _decide() there's code to memcpy()-convert them to a float. // Round 340, 223.4 points, length 39, 36% stopped, 64% died // const uint32_t _weights[36] = {0xbd8e626e, 0xbee2cd2c, 0x3e4d5cab, 0x3eceb8c3, 0xbed0a514, 0x3ec62438, 0x3e947ed4, 0xbe4b8bf2, 0xbf301113, 0xbf3f0a75, 0x3f1868f7, 0xbf0253ca, 0xbedca2f2, 0xbd547c6d, 0x3edd6a8a, 0xbd4b97b6, 0x3f64ec26, 0xbe5323c1, 0x3eccf87d, 0xbf2d4796, 0xbf62b6e8, 0xbf71daf6, 0xbf03f08e, 0xbf222609, 0x3e26c03c, 0xbf497837, 0xbee4d175, 0x3ec601de, 0x3e4e0695, 0x3eef2619, 0xbe849370, 0xbf18fb2b, 0x3f25bbd1, 0xbf3dcd78, 0x3f37a58d, 0x3ef4a25b}; // Round 630, 221.0 points, length 38, 36% stopped, 64% died const uint32_t _weights[36] = {0xbd25943f, 0xbf279d81, 0x3e25d128, 0x3ec62438, 0x3f0e719c, 0x3eefbea9, 0x3e947ed4, 0xbe5323c1, 0xbf2d4796, 0xbf3f0a75, 0x3f0e45d9, 0xbf0253ca, 0xbedca2f2, 0xbd79073c, 0x3ede80ec, 0xbd4b97b6, 0x3f69a6be, 0xbe4b8bf2, 0x3eccf87d, 0xbf301113, 0xbf62b6e8, 0xbf71daf6, 0xbf204130, 0xbf222609, 0x3e26c03c, 0xbf497837, 0xbee4d175, 0x3ec601de, 0x3e4954eb, 0x3eef2619, 0xbe849370, 0xbf18fb2b, 0x3f25bbd1, 0xbf3b4e44, 0x3f484d59, 0x3edd6a8a}; const uint8_t _net_layout[3] = {6, 4, 3}; const uint8_t _net_layers = 3; const uint8_t _net_total_size = 36; uint16_t _xy2i(uint8_t x, uint8_t y); uint16_t _xy2i(Coords c); Coords _i2xy(uint16_t i); Coords _new_pos(uint8_t dir); uint8_t _dying = 0; bool _is_free(uint8_t dir); uint8_t _free_spaces(uint8_t dir); uint8_t _to_apple(uint8_t dir); void _place_apple(); void _init(); void _decide(); int8_t _manual_decision(); void _move(); void _draw(); public: SnakeEffect(); ~SnakeEffect(); void loop(uint16_t ms); boolean can_be_shown_with_clock(); String get_name() override { return "snake"; } };