source: cpp/frams/genetics/fB/fB_conv.cpp @ 780

Last change on this file since 780 was 780, checked in by Maciej Komosinski, 6 years ago

Added sources for genetic encodings fB, fH, fL

File size: 4.6 KB
Line 
1#include "fB_conv.h"
2
3#include <frams/param/paramobj.h>
4#include <vector>
5#include <frams/util/multimap.h>
6#include "fB_general.h"
7
8double GenoConv_fBH::convertCharacterTo01(char c)
9{
10        return (double)(c - 'a') / 25.0;
11}
12
13double GenoConv_fBH::convertCharacterToWeight(char c)
14{
15        if (c <= 'm')
16        {
17                return -0.001 * pow(2.0, (double)('m' - c));
18        }
19        else
20        {
21                return 0.001 * pow(2.0, (double)(c - 'n'));
22        }
23}
24
25fH_Handle* GenoConv_fBH::convertCharacterToHandle(char c, int dims, int start, int end, std::vector<IRange> ranges[3])
26{
27        fH_Handle *handle = NULL;
28        if (c >= 'a' && c <= 'i')
29        {
30                handle = new fH_StickHandle(dims, start, end);
31                ranges[0].push_back(IRange(start, end));
32        }
33        else if (c >= 'j' && c <= 'p')
34        {
35                handle = new fH_NeuronHandle(dims, start, end);
36                ranges[1].push_back(IRange(start, end));
37        }
38        else
39        {
40                handle = new fH_ConnectionHandle(dims, start, end);
41                ranges[2].push_back(IRange(start, end));
42        }
43        return handle;
44}
45
46SString GenoConv_fBH::convert(SString &i, MultiMap *map, bool using_checkpoints)
47{
48        // if there is no genotype to load, then return error
49
50        std::vector<IRange> ranges[3];
51
52        int pos = 0;
53        SString line;
54        i.getNextToken(pos, line, '\n');
55        int dims = 0;
56        // extract dimensions
57        if (!ExtValue::parseInt(line.c_str(), dims, true, false))
58        {
59                logMessage("f2::Builder", "parseGenotype", LOG_ERROR, "Could not parse number of dimensions");
60                return "";
61        }
62
63        if (dims < 1)
64        {
65                logMessage("f2::Builder", "parseGenotype", LOG_ERROR, "Number of dimensions cannot be lower than 1");
66                return 1;
67        }
68
69        fH_Builder creature(dims, false);
70
71        for (int q = 0; q < fB_GenoHelpers::geneCount(i); q++)
72        {
73                int start, end;
74                SString gene = fB_GenoHelpers::getGene(q, i, start, end);
75                end -= 1; // last character is included in range, so decrementation is required
76                int endoffset = 0;
77                if (gene.indexOf("zz", 0) != -1) endoffset = 2;
78                if (gene.len() - endoffset < 3)
79                {
80                        fH_StickHandle *handle = new fH_StickHandle(dims, start, end);
81                        ParamEntry *tab = creature.getParamTab(handle->type);
82                        void *obj = ParamObject::makeObject(tab);
83                        Param par(tab, NULL);
84                        par.select(obj);
85                        par.setDefault();
86                        handle->loadProperties(par);
87                        ranges[0].push_back(IRange(start, end));
88                        creature.addHandle(handle);
89                        continue;
90                }
91                fH_Handle *handle = convertCharacterToHandle(gene[2], dims, start, end, ranges);
92                ParamEntry *tab = creature.getParamTab(handle->type);
93                void *obj = ParamObject::makeObject(tab);
94                Param par(tab, NULL);
95                par.select(obj);
96                par.setDefault();
97
98                int propindex = 0;
99                int z = 3;
100                endoffset = 0;
101                if (gene.indexOf("zz", 0) != -1) endoffset = 2;
102                while (z < gene.len() - endoffset)
103                {
104                        if (processNextLetter(creature, handle, par, gene, propindex, z, ranges) == -1)
105                        {
106                                logMessage("GenoConv_fBH", "convert", LOG_WARN, "Property of fH could not be parsed");
107                        }
108                }
109                handle->loadProperties(par);
110                creature.addHandle(handle);
111        }
112
113        SString fHgenotype = creature.toString();
114
115        if (NULL != map)
116        {
117                int fHpos = 0;
118                SString line;
119                fHgenotype.getNextToken(fHpos, line, '\n');
120                int lastpos = fHpos;
121                for (int t = 0; t < 3; t++)
122                {
123                        for (unsigned int q = 0; q < ranges[t].size(); q++)
124                        {
125                                fHgenotype.getNextToken(fHpos, line, '\n');
126                                map->add(ranges[t][q].begin, ranges[t][q].end, lastpos, fHpos - 1);
127                        }
128                }
129        }
130
131        return fHgenotype;
132}
133
134int GenoConv_fBH::processNextLetter(fH_Builder &creature, fH_Handle *&currhandle, Param &par, SString gene, int &propindex, int &i, std::vector<IRange> ranges[3])
135{
136        if (propindex >= par.getPropCount())
137        {
138                int tmpend = currhandle->end;
139                currhandle->end = i - 1;
140                currhandle->loadProperties(par);
141                creature.addHandle(currhandle);
142                currhandle = convertCharacterToHandle(gene[i], currhandle->getDimensions(), currhandle->begin + i, tmpend, ranges);
143                ParamEntry *tab = creature.getParamTab(currhandle->type);
144                par.setParamTab(tab);
145                void *obj = ParamObject::makeObject(tab);
146                par.select(obj);
147                par.setDefault();
148                propindex = 0;
149                i++;
150                return 0;
151        }
152        else
153        {
154                if (*par.type(propindex) == 'f')
155                {
156                        if (currhandle->type == fHBodyType::CONNECTION && *par.id(propindex) == 'w')
157                        {
158                                par.setDouble(propindex, convertCharacterToWeight(gene[i]));
159                        }
160                        else
161                        {
162                                double val = convertCharacterTo01(gene[i]);
163                                double mn, mx, def;
164                                par.getMinMaxDouble(propindex, mn, mx, def);
165                                par.setDouble(propindex, min(mx, max(mn, (mx - mn) * val + mn)));
166                        }
167                        propindex++;
168                        i++;
169                        return 0;
170                }
171                else if (currhandle->type == fHBodyType::NEURON && *par.id(propindex) == 'd')
172                {
173                        //TODO: handle neuron classes and properties
174                        propindex++;
175                        i++;
176                        return 0;
177                }
178                // other property types are not available in this encoding
179                return -1;
180        }
181}
Note: See TracBrowser for help on using the repository browser.