board_gamma_update(): Don't crash if not board->gamma
[pachi/t.git] / pattern.h
blobe0c3ee5fe705cd2be3b069ec17a225e5bceaca35
1 #ifndef ZZGO_PATTERN_H
2 #define ZZGO_PATTERN_H
4 /* Matching of multi-featured patterns. */
6 #include "board.h"
7 #include "move.h"
9 /* When someone says "pattern", you imagine a configuration of stones in given
10 * area (e.g. as matched very efficiently by pattern3 in case of 3x3 area).
11 * However, we use a richer definition of pattern, where this is merely one
12 * pattern _feature_. Another features may be is-a-selfatari, is-a-capture,
13 * number of liberties, distance from last move, etc. */
15 /* ! NOTE NOTE NOTE ! We provide infrastructure for matching patterns, but we
16 * also replicate the most bare-bone part of it for tiny subset of features
17 * in board.c:board_gamma_update() for fast incremental probability
18 * distribution maintenance. Aside of using the constants defined here, that
19 * implementation is completely independent and does not call back here. */
21 /* Each feature is represented by its id and an optional 32-bit payload;
22 * when matching, discrete (id,payload) pairs are considered. */
24 /* This is heavily influenced by (Coulom, 2007), of course. */
25 /* TODO: Try completely separate ko / no-ko features. */
27 /* See the HACKING file for another description of the pattern matcher and
28 * instructions on how to harvest and inspect patterns. */
30 /* If you add a payload bit for a feature, don't forget to update the value
31 * in feature_info. */
32 enum feature_id {
33 /* Implemented: */
35 /* This is a pass. */
36 /* Payload: [bit0] Last move was also pass? */
37 #define PF_PASS_LASTPASS 0
38 FEAT_PASS,
40 /* Simple capture move. */
41 /* Payload: [bit0] Capturing laddered group? */
42 #define PF_CAPTURE_LADDER 0
43 /* [bit1] Re-capturing last move? */
44 #define PF_CAPTURE_RECAPTURE 1 /* TODO */
45 /* [bit2] Enables our atari group get more libs? */
46 #define PF_CAPTURE_ATARIDEF 2
47 /* [bit3] Capturing ko? */
48 #define PF_CAPTURE_KO 3
49 FEAT_CAPTURE,
51 /* Atari escape (extension). */
52 /* Payload: [bit0] Escaping with laddered group? */
53 #define PF_AESCAPE_LADDER 0
54 FEAT_AESCAPE,
56 /* Self-atari move. */
57 /* Payload: [bit0] Also using our complex definition? */
58 #define PF_SELFATARI_SMART 0
59 FEAT_SELFATARI,
61 /* Atari move. */
62 /* Payload: [bit0] The atari'd group gets laddered? */
63 #define PF_ATARI_LADDER 0
64 /* [bit1] Playing ko? */
65 #define PF_ATARI_KO 1
66 FEAT_ATARI,
68 /* Border distance. */
69 /* Payload: The distance - "line number". Only up to 4. */
70 FEAT_BORDER,
72 /* Last move distance. */
73 /* Payload: The distance - gridcular metric. */
74 FEAT_LDIST,
76 /* Next-to-last move distance. */
77 /* Payload: The distance - gridcular metric. */
78 FEAT_LLDIST,
80 /* Continuity. */
81 /* Payload: [bit0] The move is in 8-neighborhood of last move (ldist<=3) */
82 /* This is a fast substitution to ldist/lldist. */
83 FEAT_CONTIGUITY,
85 /* Spatial configuration of stones in certain board area,
86 * with black to play. */
87 /* Payload: Index in the spatial_dict. */
88 FEAT_SPATIAL,
90 /* Spatial configuration of stones in fixed 3x3 square,
91 * with black to play. */
92 /* This is a fast substitution to spatial. */
93 /* Payload: Pattern3 hash (see pattern3.h). */
94 /* Note that the hash describes only one particular rotation;
95 * no normalization across rotations and transpositions is done
96 * during the matching, only color normalization. The patternscan
97 * and gamma machineries is taking care of the rotations. */
98 FEAT_PATTERN3,
101 /* Unimplemented - TODO: */
103 /* Monte-carlo owner. */
104 /* Payload: #of playouts owning this point at the final
105 * position, scaled to 0..15 (lowest 4 bits). */
106 FEAT_MCOWNER,
108 FEAT_MAX
111 struct feature {
112 enum feature_id id;
113 uint16_t payload;
116 struct pattern {
117 /* Pattern (matched) is set of features. */
118 int n;
119 #define FEATURES 32
120 struct feature f[FEATURES];
123 struct spatial_dict;
124 struct pattern_config {
125 /* FEAT_SPATIAL: Generate patterns only for these sizes (gridcular). */
126 int spat_min, spat_max;
127 /* FEAT_BORDER: Generate features only up to this board distance. */
128 int bdist_max;
129 /* FEAT_LDIST, FEAT_LLDIST: Generate features only for these move
130 * distances. */
131 int ldist_min, ldist_max;
132 /* FEAT_MCOWNER: Generate feature after this number of simulations. */
133 int mcsims;
135 /* The spatial patterns dictionary, used by FEAT_SPATIAL. */
136 struct spatial_dict *spat_dict;
138 extern struct pattern_config DEFAULT_PATTERN_CONFIG;
139 extern struct pattern_config FAST_PATTERN_CONFIG;
141 /* The pattern_spec[] specifies which features to tests for;
142 * highest bit controls whether to test for the feature at all,
143 * then for bitmap features (except FEAT_SPATIAL) the rest
144 * of the bits controls various PF tests; for non-bitmap
145 * features, you will need to tweak the patternconfig to
146 * fine-tune them. */
147 typedef uint16_t pattern_spec[FEAT_MAX];
148 /* Match all supported features. */
149 extern pattern_spec PATTERN_SPEC_MATCHALL;
150 /* Match only "quick" features, suitable for MC simulations. */
151 extern pattern_spec PATTERN_SPEC_MATCHFAST;
154 /* Append feature to string. */
155 char *feature2str(char *str, struct feature *f);
156 /* Convert string to feature, return pointer after the featurespec. */
157 char *str2feature(char *str, struct feature *f);
158 /* Get name of given feature. */
159 char *feature_name(enum feature_id f);
160 /* Get number of possible payload values associated with the feature. */
161 int feature_payloads(struct pattern_config *pc, enum feature_id f);
163 /* Append pattern as feature spec string. */
164 char *pattern2str(char *str, struct pattern *p);
166 /* Initialize p and fill it with features matched by the
167 * given board move. */
168 void pattern_match(struct pattern_config *pc, pattern_spec ps, struct pattern *p, struct board *b, struct move *m);
171 /* Comparative strengths of all feature-payload pairs (initialized to 1 for
172 * unspecified pairs). */
173 struct features_gamma {
174 /* Indexed by feature and payload; each feature array is allocated for
175 * all possible payloads to fit in. */
176 float *gamma[FEAT_MAX];
177 struct pattern_config *pc;
179 /* Default gamma filename to use. */
180 extern const char *features_gamma_filename;
182 /* Initializes gamma values, pre-loading existing records from given file
183 * (NULL for default), falling back to gamma==1 for unspecified values. */
184 struct features_gamma *features_gamma_init(struct pattern_config *pc, const char *file);
186 /* Look up gamma of given feature, or set one if gamma is not NULL. */
187 static float feature_gamma(struct features_gamma *fg, struct feature *f, float *gamma);
189 /* Destroy the structure. */
190 void features_gamma_done(struct features_gamma *fg);
193 static inline float
194 feature_gamma(struct features_gamma *fg, struct feature *f, float *gamma)
196 if (gamma) fg->gamma[f->id][f->payload] = *gamma;
197 return fg->gamma[f->id][f->payload];
200 #endif