1 /* "Species" - a CoreWars evolver. Copyright (C) 2003 'Varfar'
2 *
3 * This program is free software; you can redistribute it and/or modify it
4 * under the terms of the GNU General Public License as published by the Free
5 * Software Foundation; either version 1, or (at your option) any later
6 * version.
7 *
8 * This program is distributed in the hope that it will be useful, but WITHOUT
9 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
10 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
11 * more details.
12 *
13 * You should have received a copy of the GNU General Public License along
14 * with this program; if not, write to the Free Software Foundation, Inc.,
15 * 675 Mass Ave, Cambridge, MA 02139, USA.
16 */
17
18 #include "operand.hpp"
19
20 // concrete implementation headers
21 #include "operand_distribution.hpp"
22 #include "operand_table.hpp"
23
24 #include "species.hpp"
25 #include "rand.hpp"
26
27 //#include <string.h>
28
29 /************ COperand implementation ****************************/
30
31 const char *COperand::IMPL_DESC[COperand::IMPL_LAST] = { "distribution","table" };
32 const char *COperand::TYPE_KEY = "operands";
33
impl_desc(const COperand::IMPL type)34 const char *COperand::impl_desc(const COperand::IMPL type) {
35 if((type >= 0) && (type < IMPL_LAST))
36 return IMPL_DESC[type];
37 return 0; // bad
38 }
39
desc_to_impl(const char * desc)40 COperand::IMPL COperand::desc_to_impl(const char *desc) {
41 for(int i=0; i<IMPL_LAST; i++) {
42 if(strcasecmp(desc,IMPL_DESC[i])==0)
43 return (IMPL)i;
44 }
45 PANIC(MISC,"bad ",type_key());
46 }
47
COperand(const field_t coresize)48 COperand::COperand(const field_t coresize) {
49 _coresize = coresize;
50 }
51
NewDefault(const field_t coresize)52 COperand *COperand::NewDefault(const field_t coresize) {
53 return new COperandDistribution(coresize);
54 }
55
read_ini(INIFile & ini,const field_t coresize)56 COperand *COperand::read_ini(INIFile &ini,const field_t coresize) {
57 KeyValuePair *kvp;
58 COperand *ret;
59 // identify which implementation, based upon keywords
60 kvp = ini.get(type_key());
61 if(0 == kvp) { // not specified? we have a default..
62 ret = NewDefault(coresize);
63 } else {
64 switch(desc_to_impl(kvp->getValueAsChar())) {
65 case DISTRIBUTION:
66 ret = new COperandDistribution(coresize);
67 break;
68 case TABLE:
69 ret = new COperandTable(coresize);
70 break;
71 default:
72 PANIC(MISC,kvp->getValueAsChar(),type_key());
73 }
74 }
75 ret->read_ini_impl(ini);
76 return ret;
77 }
78
read_override_ini(COperand * gen,INIFile & ini)79 COperand *COperand::read_override_ini(COperand *gen,INIFile &ini) {
80 KeyValuePair *kvp;
81 COperand *ret;
82 // identify which implementation, based upon keywords
83 kvp = ini.get(type_key());
84 if(0 == kvp) return gen; // nothing to do?
85 switch(desc_to_impl(kvp->getValueAsChar())) {
86 case DISTRIBUTION:
87 if(same_type(gen,ret)) {
88 ret = new COperandDistribution((COperandDistribution&)*gen);
89 ret->read_override_ini_impl(ini);
90 } else {
91 ret = new COperandDistribution(ret->_coresize);
92 ret->read_ini_impl(ini);
93 }
94 break;
95 case TABLE:
96 if(same_type(gen,ret)) {
97 ret = new COperandTable((COperandTable&)*gen);
98 ret->read_override_ini_impl(ini);
99 } else {
100 ret = new COperandTable(ret->_coresize);
101 ret->read_ini_impl(ini);
102 }
103 break;
104 default:
105 PANIC(MISC,kvp->getValueAsChar(),type_key());
106 }
107 return ret;
108 }
109