43
46
////////////////////////////////////////////////////////////////////////
46
struct AtomInfo::atomname
47
AtomInfo::names_[MaxZ] =
49
{"hydrogen", "H"}, // 1
50
{"helium", "He"}, // 2
51
{"lithium", "Li"}, // 3
52
{"beryllium", "Be"}, // 4
55
{"nitrogen", "N"}, // 7
57
{"fluorine", "F"}, // 9
59
{"sodium", "Na"}, // 11
60
{"magnesium", "Mg"}, // 12
61
{"aluminum", "Al"}, // 13
62
{"silicon", "Si"}, // 14
63
{"phosphorus" ,"P"}, // 15
64
{"sulfur", "S"}, // 16
65
{"chlorine", "Cl"}, // 17
66
{"argon", "Ar"}, // 18
67
{"potassium", "K"}, // 19
68
{"calcium", "Ca"}, // 20
69
{"scandium", "Sc"}, // 21
70
{"titanium", "Ti"}, // 22
71
{"vanadium", "V"}, // 23
72
{"chromium", "Cr"}, // 24
73
{"manganese", "Mn"}, // 25
75
{"cobalt", "Co"}, // 27
76
{"nickel", "Ni"}, // 28
77
{"copper", "Cu"}, // 29
79
{"gallium", "Ga"}, // 31
80
{"germanium", "Ge"}, // 32
81
{"arsenic", "As"}, // 33
82
{"selenium", "Se"}, // 34
83
{"bromine", "Br"}, // 35
84
{"krypton", "Kr"}, // 36
85
{"rubidium", "Rb"}, // 37
86
{"strontium", "Sr"}, // 38
87
{"yttrium", "Y"}, // 39
88
{"zirconium", "Zr"}, // 40
89
{"niobium", "Nb"}, // 41
90
{"molybdenum", "Mo"}, // 42
91
{"technetium", "Tc"}, // 43
92
{"ruthenium", "Ru"}, // 44
93
{"rhodium", "Rh"}, // 45
94
{"palladium", "Pd"}, // 46
95
{"silver", "Ag"}, // 47
96
{"cadminium", "Cd"}, // 48
97
{"indium", "In"}, // 49
99
{"antimony", "Sb"}, // 51
100
{"tellurium", "Te"}, // 52
101
{"iodine", "I"}, // 53
102
{"xenon", "Xe"}, // 54
103
{"cesium", "Cs"}, // 55
104
{"barium", "Ba"}, // 56
105
{"lanthanium", "La"}, // 57
106
{"cerium", "Ce"}, // 58
107
{"praseodymium", "Pr"}, // 59
108
{"neodymium", "Nd"}, // 60
109
{"promethium", "Pm"}, // 61
110
{"samarium", "Sm"}, // 62
111
{"europium", "Eu"}, // 63
112
{"gadolinium", "Gd"}, // 64
113
{"terbium", "Tb"}, // 65
114
{"dysprosium", "Dy"}, // 66
115
{"holmium", "Ho"}, // 67
116
{"erbium", "Er"}, // 68
117
{"thulium", "Tm"}, // 69
118
{"ytterbium", "Yb"}, // 70
119
{"lutetium", "Lu"}, // 71
120
{"hafnium", "Hf"}, // 72
121
{"tantalum", "Ta"}, // 73
122
{"tungsten", "W"}, // 74
123
{"rhenium", "Re"}, // 75
124
{"osmium", "Os"}, // 76
125
{"iridium", "Ir"}, // 77
126
{"platinum", "Pt"}, // 78
127
{"gold", "Au"}, // 79
128
{"mercury", "Hg"}, // 80
129
{"thallium", "Tl"}, // 81
130
{"lead", "Pb"}, // 82
131
{"bismuth", "Bi"}, // 83
132
{"polonium", "Po"}, // 84
133
{"astatine", "At"}, // 85
134
{"radon", "Rn"}, // 86
135
{"francium", "Fr"}, // 87
136
{"radium", "Ra"}, // 88
137
{"actinium", "Ac"}, // 89
138
{"thorium", "Th"}, // 90
139
{"protactinium", "Pa"}, // 91
140
{"uranium", "U"}, // 92
141
{"neptunium", "Np"}, // 93
142
{"plutonium", "Pu"}, // 94
143
{"americium", "Am"}, // 95
144
{"curium", "Cm"}, // 96
145
{"berkelium", "Bk"}, // 97
146
{"californium", "Cf"}, // 98
147
{"einsteinum", "Es"}, // 99
148
{"fermium", "Fm"}, // 100
149
{"mendelevium", "Md"}, // 101
150
{"nobelium", "No"}, // 102
151
{"lawrencium", "Lr"}, // 103
152
{"rutherfordium","Rf"}, // 104
153
{"hahnium", "Ha"}, // 105
154
{"Unnamed", "Un"}, // 106
155
{"Unnamed", "Un"} // 107
50
AtomInfo::elements_[Nelement] =
51
{{1, "hydrogen", "H"},
54
{4, "beryllium", "Be"},
62
{12, "magnesium", "Mg"},
63
{13, "aluminum", "Al"},
64
{14, "silicon", "Si"},
65
{15, "phosphorus" ,"P"},
67
{17, "chlorine", "Cl"},
69
{19, "potassium", "K"},
70
{20, "calcium", "Ca"},
71
{21, "scandium", "Sc"},
72
{22, "titanium", "Ti"},
73
{23, "vanadium", "V"},
74
{24, "chromium", "Cr"},
75
{25, "manganese", "Mn"},
81
{31, "gallium", "Ga"},
82
{32, "germanium", "Ge"},
83
{33, "arsenic", "As"},
84
{34, "selenium", "Se"},
85
{35, "bromine", "Br"},
86
{36, "krypton", "Kr"},
87
{37, "rubidium", "Rb"},
88
{38, "strontium", "Sr"},
90
{40, "zirconium", "Zr"},
91
{41, "niobium", "Nb"},
92
{42, "molybdenum", "Mo"},
93
{43, "technetium", "Tc"},
94
{44, "ruthenium", "Ru"},
95
{45, "rhodium", "Rh"},
96
{46, "palladium", "Pd"},
98
{48, "cadminium", "Cd"},
101
{51, "antimony", "Sb"},
102
{52, "tellurium", "Te"},
105
{55, "cesium", "Cs"},
106
{56, "barium", "Ba"},
107
{57, "lanthanium", "La"},
108
{58, "cerium", "Ce"},
109
{59, "praseodymium", "Pr"},
110
{60, "neodymium", "Nd"},
111
{61, "promethium", "Pm"},
112
{62, "samarium", "Sm"},
113
{63, "europium", "Eu"},
114
{64, "gadolinium", "Gd"},
115
{65, "terbium", "Tb"},
116
{66, "dysprosium", "Dy"},
117
{67, "holmium", "Ho"},
118
{68, "erbium", "Er"},
119
{69, "thulium", "Tm"},
120
{70, "ytterbium", "Yb"},
121
{71, "lutetium", "Lu"},
122
{72, "hafnium", "Hf"},
123
{73, "tantalum", "Ta"},
124
{74, "tungsten", "W"},
125
{75, "rhenium", "Re"},
126
{76, "osmium", "Os"},
127
{77, "iridium", "Ir"},
128
{78, "platinum", "Pt"},
130
{80, "mercury", "Hg"},
131
{81, "thallium", "Tl"},
133
{83, "bismuth", "Bi"},
134
{84, "polonium", "Po"},
135
{85, "astatine", "At"},
137
{87, "francium", "Fr"},
138
{88, "radium", "Ra"},
139
{89, "actinium", "Ac"},
140
{90, "thorium", "Th"},
141
{91, "protactinium", "Pa"},
142
{92, "uranium", "U"},
143
{93, "neptunium", "Np"},
144
{94, "plutonium", "Pu"},
145
{95, "americium", "Am"},
146
{96, "curium", "Cm"},
147
{97, "berkelium", "Bk"},
148
{98, "californium", "Cf"},
149
{99, "einsteinum", "Es"},
150
{100, "fermium", "Fm"},
151
{101, "mendelevium", "Md"},
152
{102, "nobelium", "No"},
153
{103, "lawrencium", "Lr"},
154
{104, "rutherfordium","Rf"},
155
{105, "hahnium", "Ha"},
156
{106, "seaborgium", "Sg"},
157
{107, "bohrium", "Bh"},
158
{108, "hassium", "Hs"},
159
{109, "meitnerium", "Mt"},
160
{110, "darmstadtium", "Ds"},
161
{111, "roentgenium", "Rg"},
162
{112, "ununbium", "Uub"},
163
{113, "ununtrium", "Uut"},
164
{114, "ununquadium", "Uuq"},
165
{115, "ununpentium", "Uup"},
166
{116, "ununhexium", "Uuh"},
167
{117, "ununseptium", "Uus"},
168
{118, "ununoctium", "Uuo"}
158
171
static ClassDesc AtomInfo_cd(
234
AtomInfo::initialize_names()
236
for (int i=0; i<Nelement; i++) {
237
symbol_to_Z_[elements_[i].symbol] = elements_[i].Z;
238
name_to_Z_[elements_[i].name] = elements_[i].Z;
241
// Z == DefaultZ is reserved for default values
242
symbol_to_Z_["Def"] = DefaultZ;
243
name_to_Z_["default"] = DefaultZ;
245
// Z == 1000 is reserved for point charges
246
name_to_Z_["charge"] = 1000;
247
symbol_to_Z_["Q"] = 1000;
249
for (std::map<std::string,int>::iterator i = symbol_to_Z_.begin();
250
i != symbol_to_Z_.end(); i++) {
251
Z_to_symbols_[i->second] = i->first;
254
for (std::map<std::string,int>::iterator i = name_to_Z_.begin();
255
i != name_to_Z_.end(); i++) {
256
Z_to_names_[i->second] = i->first;
244
261
AtomInfo::load_library_values()
246
263
Ref<MessageGrp> grp = MessageGrp::get_default_messagegrp();
264
sc::auto_vec<char> in_char_array;
247
265
if (grp->me() == 0) {
248
266
const char* libdir;
267
std::string filename;
250
268
if ((libdir = getenv("SCLIBDIR")) != 0) {
251
269
const char* atominfo = "/atominfo.kv";
252
270
const char *eq = ::strchr(libdir,'=');
253
271
if (eq) libdir = eq + 1;
254
char *filename = new char[strlen(libdir) + strlen(atominfo) + 1];
255
strcpy(filename, libdir);
256
strcat(filename, atominfo);
257
keyval = new ParsedKeyVal(filename);
272
filename = std::string(libdir) + atominfo;
265
279
ainfo = SRC_SCLIBDIR "/atominfo.kv";
268
ExEnv::out0() << indent << "Reading file " << ainfo << "." << endl;
269
keyval = new ParsedKeyVal(ainfo);
271
Ref<KeyVal> pkeyval = new PrefixKeyVal(keyval, "atominfo");
272
load_values(pkeyval,0);
274
grp->bcast(mass_,MaxZ);
275
grp->bcast(atomic_radius_,MaxZ);
276
grp->bcast(vdw_radius_,MaxZ);
277
grp->bcast(bragg_radius_,MaxZ);
278
grp->bcast(maxprob_radius_,MaxZ);
279
grp->bcast(atomic_radius_scale_);
280
grp->bcast(vdw_radius_scale_);
281
grp->bcast(bragg_radius_scale_);
282
grp->bcast(maxprob_radius_scale_);
283
for (int i=0; i<MaxZ; i++) grp->bcast(rgb_[i],3);
284
grp->bcast(ip_,MaxZ);
284
ExEnv::out0() << indent << "Reading file " << filename << "." << endl;
285
ifstream is(filename.c_str());
288
int n = 1 + strlen(ostrs.str().c_str());
289
in_char_array.reset(strcpy(new char[n],ostrs.str().c_str()));
291
grp->bcast(in_char_array.get(), n);
296
in_char_array.reset(new char[n]);
297
grp->bcast(in_char_array.get(), n);
300
Ref<ParsedKeyVal> keyval = new ParsedKeyVal();
301
keyval->parse_string(in_char_array.get());
302
Ref<KeyVal> pkeyval = new PrefixKeyVal(keyval.pointer(), "atominfo");
303
load_values(pkeyval,0);
297
316
Ref<Units> bohr = new Units("bohr");
298
317
Ref<Units> hartree = new Units("hartree");
300
load_values(mass_, 0, "mass", keyval, override, amu);
301
load_values(atomic_radius_, &atomic_radius_scale_, "atomic_radius",
302
keyval, override, bohr);
303
load_values(vdw_radius_, &vdw_radius_scale_, "vdw_radius",
304
keyval, override, bohr);
305
load_values(bragg_radius_, &bragg_radius_scale_,
319
load_values(Z_to_mass_, 0, "mass", keyval, override, amu);
320
load_values(Z_to_atomic_radius_, &atomic_radius_scale_, "atomic_radius",
321
keyval, override, bohr);
322
load_values(Z_to_vdw_radius_, &vdw_radius_scale_, "vdw_radius",
323
keyval, override, bohr);
324
load_values(Z_to_bragg_radius_, &bragg_radius_scale_,
306
325
"bragg_radius", keyval, override, bohr);
307
load_values(maxprob_radius_, &maxprob_radius_scale_,
326
load_values(Z_to_maxprob_radius_, &maxprob_radius_scale_,
308
327
"maxprob_radius", keyval, override, bohr);
309
load_values(rgb_, "rgb", keyval, override);
310
load_values(ip_, 0, "ip", keyval, override, hartree);
328
load_values(Z_to_rgb_, "rgb", keyval, override);
329
load_values(Z_to_ip_, 0, "ip", keyval, override, hartree);
314
AtomInfo::load_values(double *array, double *scale, const char *keyword,
333
AtomInfo::load_values(std::map<int,double>&values,
334
double *scale, const char *keyword,
315
335
const Ref<KeyVal> &keyval, int override,
316
336
const Ref<Units> &units)
446
AtomInfo::string_to_Z(const char *name, int allow_exceptions)
470
AtomInfo::string_to_Z(const std::string &name, int allow_exceptions)
451
474
// see if the name is a atomic number
454
// name is not an atomic number--must be a symbol or atom name
457
// convert the name to lower case
458
char* tmpname = strdup(name);
459
for (j=0; j<strlen(tmpname); j++) {
460
if (isupper(tmpname[j])) tmpname[j] = tolower(tmpname[j]);
463
// loop thru the elements, looking for a match
464
for (i=0; i<MaxZ; i++) {
466
// see if an atom name matches
467
// if we find a match we are done looping
468
if (!strcmp(names_[i].name,tmpname)) {
473
// see if an atomic symbol (converted to lower case) matches
474
char* tmpsymbol = strdup(names_[i].symbol);
475
for (j=0; j<strlen(tmpsymbol); j++) {
476
if (isupper(tmpsymbol[j])) tmpsymbol[j] = tolower(tmpsymbol[j]);
478
// if we find a match we are done looping
479
if (!strcmp(tmpsymbol,tmpname)) {
487
// free the lowercase version of the name
491
// check to see if z value is OK, if not then the name must have been
493
if (Z < 1 || Z > MaxZ) {
494
if (allow_exceptions) {
496
<< sprintf("AtomInfo: invalid name: %s\n",name);
475
Z = atoi(name.c_str());
478
// convert the name to lower case
479
std::string tmpname(name);
480
for (int j=0; j<tmpname.size(); j++) {
481
if (isupper(tmpname[j])) tmpname[j] = tolower(tmpname[j]);
484
std::map<std::string,int>::const_iterator iname
485
= name_to_Z_.find(tmpname);
486
if (iname != name_to_Z_.end()) return iname->second;
488
if (tmpname.size() > 0) {
489
if (islower(tmpname[0])) tmpname[0] = toupper(tmpname[0]);
492
iname = symbol_to_Z_.find(tmpname);
493
if (iname != symbol_to_Z_.end()) return iname->second;
495
if (allow_exceptions) {
496
ExEnv::err0() << sprintf("AtomInfo: invalid name: %s\n",name.c_str());
497
throw std::runtime_error("invalid atom name");
504
AtomInfo::lookup_value(const std::map<int,double>& values, int Z) const
506
std::map<int,double>::const_iterator found = values.find(Z);
507
if (found == values.end()) {
508
found = values.find(DefaultZ);
510
return found->second;
514
AtomInfo::lookup_array_value(const std::map<int,std::vector<double> >& values,
517
std::map<int,std::vector<double> >::const_iterator found = values.find(Z);
518
if (found == values.end()) {
519
found = values.find(DefaultZ);
521
return found->second[i];
525
AtomInfo::vdw_radius(int Z) const
527
return lookup_value(Z_to_vdw_radius_,Z)*vdw_radius_scale_;
531
AtomInfo::bragg_radius(int Z) const
533
return lookup_value(Z_to_bragg_radius_,Z)*bragg_radius_scale_;
537
AtomInfo::atomic_radius(int Z) const
539
return lookup_value(Z_to_atomic_radius_,Z)*atomic_radius_scale_;
543
AtomInfo::maxprob_radius(int Z) const
545
return lookup_value(Z_to_maxprob_radius_,Z)*maxprob_radius_scale_;
549
AtomInfo::ip(int Z) const
551
return lookup_value(Z_to_ip_,Z);
555
AtomInfo::rgb(int Z, int color) const
557
return lookup_array_value(Z_to_rgb_,Z,color);
561
AtomInfo::red(int Z) const
563
return lookup_array_value(Z_to_rgb_,Z,0);
567
AtomInfo::green(int Z) const
569
return lookup_array_value(Z_to_rgb_,Z,1);
573
AtomInfo::blue(int Z) const
575
return lookup_array_value(Z_to_rgb_,Z,2);
579
AtomInfo::mass(int Z) const
581
return lookup_value(Z_to_mass_,Z);
585
AtomInfo::name(int Z)
587
std::map<int,std::string>::const_iterator found = Z_to_names_.find(Z);
588
if (found == Z_to_names_.end()) {
589
ExEnv::err0() << scprintf("AtomInfo: invalid Z: %d\n",Z);
590
throw std::runtime_error("invalid Z");
592
return found->second;
596
AtomInfo::symbol(int Z)
598
std::map<int,std::string>::const_iterator found = Z_to_symbols_.find(Z);
599
if (found == Z_to_symbols_.end()) {
600
ExEnv::err0() << scprintf("AtomInfo: invalid Z: %d\n",Z);
601
throw std::runtime_error("invalid Z");
603
return found->second;
505
606
/////////////////////////////////////////////////////////////////////////////