00001
00002
00003
00004
00005
00006
00007
00008
00009 #ifndef __LinesTables2004_h_
00010 #define __LinesTables2004_h_
00011
00012 #include "Tools/Debugging/DebugDrawings.h"
00013 #include "Tools/Streams/InOut.h"
00014 #include "Tools/Field.h"
00015 #include "Platform/GTAssert.h"
00016
00017
00018
00019
00020
00021 class ObservationTableBase
00022 {
00023 public:
00024
00025
00026
00027
00028 virtual void write(Out& stream) const = 0;
00029
00030
00031
00032
00033
00034 virtual void read(In& stream) = 0;
00035 };
00036
00037
00038
00039
00040
00041 template<int xSize,int ySize,int cellSize,int pointRes> class ObservationTable : public ObservationTableBase
00042 {
00043 private:
00044 char point[ySize][xSize][2];
00045
00046 public:
00047 void create(const Field& field,LinesPercept::LineType type)
00048 {
00049 for(int y = 0; y < ySize; ++y)
00050 for(int x = 0; x < xSize; ++x)
00051 {
00052 Vector2<double> p = field.getClosestPoint(
00053 Vector2<double>((x + 0.5 - xSize / 2) * cellSize,
00054 (y + 0.5 - ySize / 2) * cellSize),
00055 type);
00056 point[y][x][0] = char(sgn(p.x) * int(fabs(p.x / pointRes + 0.5)));
00057 point[y][x][1] = char(sgn(p.y) * int(fabs(p.y / pointRes + 0.5)));
00058 }
00059 }
00060
00061 Vector2<double> getClosestPoint(const Vector2<double>& v) const
00062 {
00063 int x = int(v.x / cellSize + xSize / 2),
00064 y = int(v.y / cellSize + ySize / 2);
00065 if(x < 0 || x >= xSize || y < 0 || y >= ySize)
00066 return Vector2<double>(1e6,1e6);
00067 else
00068 return Vector2<double>(point[y][x][0] * pointRes,point[y][x][1] * pointRes);
00069 }
00070
00071 void draw()
00072 {
00073 for(int y = 0; y < ySize; y += 5)
00074 for(int x = 0; x < xSize; x += 5)
00075 {
00076 double x1 = (x + 0.5 - xSize / 2) * cellSize,
00077 y1 = (y + 0.5 - ySize / 2) * cellSize,
00078 x2 = point[y][x][0] * pointRes,
00079 y2 = point[y][x][1] * pointRes;
00080 if(sqrt(sqr(x1 - x2) + sqr(y1 - y2)) > 40)
00081 {
00082 LINE(selfLocatorField,x1,y1,x2,y2,
00083 0, Drawings::ps_solid,
00084 Drawings::gray);
00085 Pose2D p(atan2(y2-y1,x2-x1),Vector2<double>(x2,y2)),
00086 p2 = p + Pose2D(Vector2<double>(-50,-50)),
00087 p3 = p + Pose2D(Vector2<double>(-50,50));
00088 LINE(selfLocatorField,x2,y2,p2.translation.x,p2.translation.y,
00089 1, Drawings::ps_solid,
00090 Drawings::gray);
00091 LINE(selfLocatorField,x2,y2,p3.translation.x,p3.translation.y,
00092 1, Drawings::ps_solid,
00093 Drawings::gray);
00094 }
00095 }
00096 }
00097
00098 void write(Out& stream) const
00099 {
00100 stream.write(point,sizeof(point));
00101 }
00102
00103 void read(In& stream)
00104 {
00105 stream.read(point,sizeof(point));
00106 }
00107 };
00108
00109 inline Out& operator<<(Out& stream,const ObservationTableBase& table)
00110 {
00111 table.write(stream);
00112 return stream;
00113 }
00114
00115 inline In& operator>>(In& stream,ObservationTableBase& table)
00116 {
00117 table.read(stream);
00118 return stream;
00119 }
00120
00121
00122
00123
00124
00125 class TemplateTableBase
00126 {
00127 public:
00128
00129
00130
00131
00132 virtual void write(Out& stream) const = 0;
00133
00134
00135
00136
00137
00138 virtual void read(In& stream) = 0;
00139 };
00140
00141
00142
00143
00144
00145
00146
00147 inline Out& operator<<(Out& stream,const TemplateTableBase& table)
00148 {
00149 table.write(stream);
00150 return stream;
00151 }
00152
00153
00154
00155
00156
00157
00158
00159 inline In& operator>>(In& stream,TemplateTableBase& table)
00160 {
00161 table.read(stream);
00162 return stream;
00163 }
00164
00165
00166
00167
00168
00169 template<int TEMPLATES_MAX, int POINT_RES> class TemplateTable : public TemplateTableBase
00170 {
00171 private:
00172
00173
00174
00175 class Temp : public Pose2D
00176 {
00177 public:
00178 int distance;
00179 };
00180
00181 enum
00182 {
00183 #ifdef HUGE_FIELD
00184 DISTANCE_MAX = 650
00185 #else
00186 DISTANCE_MAX = 500
00187 #endif
00188 };
00189
00190 char templates[TEMPLATES_MAX][3];
00191 unsigned short distance[DISTANCE_MAX + 1];
00192
00193
00194
00195
00196
00197
00198
00199
00200 static int compare(const Temp* t1,const Temp* t2)
00201 {
00202 return t1->distance == t2->distance ? 0 : t1->distance < t2->distance ? -1 : 1;
00203 }
00204
00205 public:
00206
00207
00208
00209
00210
00211
00212 void create(const Field& field,LinesPercept::LineType type)
00213 {
00214 Temp* temp = new Temp[TEMPLATES_MAX];
00215 int i;
00216 double dist;
00217 for(i = 0; i < TEMPLATES_MAX; ++i)
00218 for(;;)
00219 {
00220 (Pose2D&) temp[i] = field.randomPose();
00221 dist = field.getDistance(temp[i],type);
00222 if(dist < 0)
00223 continue;
00224
00225
00226
00227
00228
00229
00230 temp[i].distance = (int) dist / 10;
00231 break;
00232 }
00233 qsort(temp,TEMPLATES_MAX,sizeof(Temp),(int (*)(const void *,const void*)) compare);
00234 i = 0;
00235 int j = 0;
00236 distance[j] = i;
00237 while(i < TEMPLATES_MAX && j < DISTANCE_MAX)
00238 {
00239 while(i < TEMPLATES_MAX && j < DISTANCE_MAX && temp[i].distance == j)
00240 {
00241 char* t = templates[i];
00242 t[0] = char(temp[i].translation.x / POINT_RES);
00243 t[1] = char(temp[i].translation.y / POINT_RES);
00244 t[2] = char(temp[i].getAngle() * 127 / pi);
00245 ++i;
00246 }
00247 distance[++j] = i;
00248 }
00249 while(j < DISTANCE_MAX)
00250 distance[++j] = i;
00251 delete [] temp;
00252 }
00253
00254
00255
00256
00257
00258
00259 Pose2D sample(double realDist) const
00260 {
00261 realDist /= 10;
00262 int dist = (int) (realDist * (0.9 + 0.2 * random()));
00263 if(dist < 0)
00264 dist = 0;
00265 else if(dist >= DISTANCE_MAX)
00266 dist = DISTANCE_MAX - 1;
00267 int index = distance[dist] + int((distance[dist + 1] - distance[dist]) * random());
00268 const char* t = templates[index < TEMPLATES_MAX ? index : TEMPLATES_MAX - 1];
00269 return Pose2D(t[2] * pi / 127,Vector2<double>(t[0] * POINT_RES,t[1] * POINT_RES));
00270 }
00271
00272 void write(Out& stream) const
00273 {
00274 stream.write(templates,sizeof(templates));
00275 stream.write(distance,sizeof(distance));
00276 }
00277
00278 void read(In& stream)
00279 {
00280 stream.read(templates,sizeof(templates));
00281 stream.read(distance,sizeof(distance));
00282 }
00283 };
00284
00285
00286
00287
00288 class LinesTables2004
00289 {
00290 public:
00291 static Field field;
00292 #ifdef HUGE_FIELD
00293 typedef ObservationTable<320,240,25,25> ObsTable;
00294 typedef TemplateTable<65000, 25> TempTable;
00295 #else
00296 typedef ObservationTable<280,200,25,20> ObsTable;
00297 typedef TemplateTable<50000, 20> TempTable;
00298 #endif
00299 static ObsTable* observationTable;
00300 static TempTable* templateTable;
00301 static int refCount;
00302
00303
00304
00305
00306 LinesTables2004();
00307
00308
00309
00310
00311 ~LinesTables2004();
00312 };
00313
00314 #endif// __LinesTables2004_h_