NetCDF-C++  4.3.1-developer
ncGroup.cpp
1 #include "ncGroup.h"
2 #include "ncVar.h"
3 #include "ncDim.h"
4 #include "ncVlenType.h"
5 #include "ncCompoundType.h"
6 #include "ncOpaqueType.h"
7 #include "ncGroupAtt.h"
8 #include "ncByte.h"
9 #include "ncUbyte.h"
10 #include "ncChar.h"
11 #include "ncShort.h"
12 #include "ncUshort.h"
13 #include "ncInt.h"
14 #include "ncUint.h"
15 #include "ncInt64.h"
16 #include "ncUint64.h"
17 #include "ncFloat.h"
18 #include "ncDouble.h"
19 #include "ncString.h"
20 #include <ncException.h>
21 #include "ncCheck.h"
22 using namespace std;
23 using namespace netCDF::exceptions;
24 
25 namespace netCDF {
26  // Global comparator operator ==============
27  // comparator operator
28  bool operator<(const NcGroup& lhs,const NcGroup& rhs)
29  {
30  return false;
31  }
32 
33  // comparator operator
34  bool operator>(const NcGroup& lhs,const NcGroup& rhs)
35  {
36  return true;
37  }
38 }
39 
40 using namespace netCDF;
41 
43 
44 NcGroup::~NcGroup()
45 {
46 }
47 
48 // Constructor generates a null object.
49 NcGroup::NcGroup() :
50  nullObject(true),
51  myId(-1)
52 {}
53 
54 
55 // constructor
56 NcGroup::NcGroup(const int groupId) :
57  nullObject(false),
58  myId(groupId)
59 { }
60 
61 // assignment operator
63 {
64  nullObject = rhs.nullObject;
65  myId = rhs.myId;
66  return *this;
67 }
68 
69 // The copy constructor.
72  myId(rhs.myId)
73 {}
74 
75 
76 // equivalence operator
77 bool NcGroup::operator==(const NcGroup & rhs) const
78 {
79  if(nullObject)
80  return nullObject == rhs.nullObject;
81  else
82  return myId == rhs.myId;
83 }
84 
85 // != operator
86 bool NcGroup::operator!=(const NcGroup & rhs) const
87 {
88  return !(*this == rhs);
89 }
90 
91 
92 // /////////////
93 // NcGroup-related methods
94 // /////////////
95 
96 // Get the group name.
97 string NcGroup::getName(bool fullName) const {
98  if(isNull()) throw NcNullGrp("Attempt to invoke NcGroup::getName on a Null group",__FILE__,__LINE__);
99  string groupName;
100  if(fullName){
101  // return full name of group with foward "/" separarating sub-groups.
102  size_t lenp;
103  ncCheck(nc_inq_grpname_len(myId,&lenp),__FILE__,__LINE__);
104  char* charName= new char[lenp+1];
105  ncCheck(nc_inq_grpname_full(myId,&lenp,charName),__FILE__,__LINE__);
106  groupName = charName;
107  delete charName;
108  }
109  else {
110  // return the (local) name of this group.
111  char charName[NC_MAX_NAME+1];
112  ncCheck(nc_inq_grpname(myId,charName),__FILE__,__LINE__);
113  groupName = charName;
114  }
115  return groupName;
116 }
117 
118 // returns true if this is the root group.
119 bool NcGroup::isRootGroup() const{
120  bool result = getName() == "/";
121  return result;
122 }
123 
124 // Get the parent group.
126  if(isNull()) throw NcNullGrp("Attempt to invoke NcGroup::getParentGroup on a Null group",__FILE__,__LINE__);
127  try {
128  int parentId;
129  ncCheck(nc_inq_grp_parent(myId,&parentId),__FILE__,__LINE__);
130  NcGroup ncGroupParent(parentId);
131  return ncGroupParent;
132  }
133  catch (NcEnoGrp& e) {
134  // no group found, so return null group
135  return NcGroup();
136  }
137 }
138 
139 
140 // Get the group id.
141 int NcGroup::getId() const {
142  if(isNull()) throw NcNullGrp("Attempt to invoke NcGroup::getId on a Null group",__FILE__,__LINE__);
143  return myId;
144 }
145 
146 // Get the number of NcGroup objects.
148  if(isNull()) throw NcNullGrp("Attempt to invoke NcGroup::getGroupCount on a Null group",__FILE__,__LINE__);
149  // initialize group counter
150  int ngroups=0;
151 
152  // record this group
153  if(location == ParentsAndCurrentGrps || location == AllGrps) {
154  ngroups ++;
155  }
156 
157  // number of children in current group
158  if(location == ChildrenGrps || location == AllChildrenGrps || location == AllGrps ) {
159  int numgrps;
160  int* ncids=NULL;
161  ncCheck(nc_inq_grps(getId(), &numgrps,ncids),__FILE__,__LINE__);
162  ngroups += numgrps;
163  }
164 
165  // search in parent groups
166  if(location == ParentsGrps || location == ParentsAndCurrentGrps || location == AllGrps ) {
167  multimap<string,NcGroup> groups(getGroups(ParentsGrps));
168  ngroups += groups.size();
169  }
170 
171 
172  // get the number of all children that are childreof children
173  if(location == ChildrenOfChildrenGrps || location == AllChildrenGrps || location == AllGrps ) {
174  multimap<string,NcGroup> groups(getGroups(ChildrenOfChildrenGrps));
175  ngroups += groups.size();
176  }
177 
178  return ngroups;
179 }
180 
181 
182 // Get the set of child NcGroup objects.
183 multimap<std::string,NcGroup> NcGroup::getGroups(NcGroup::GroupLocation location) const {
184  if(isNull()) throw NcNullGrp("Attempt to invoke NcGroup::getGroups on a Null group",__FILE__,__LINE__);
185  // create a container to hold the NcGroup's.
186  multimap<string,NcGroup> ncGroups;
187 
188  // record this group
189  if(location == ParentsAndCurrentGrps || location == AllGrps) {
190  ncGroups.insert(pair<const string,NcGroup>(getName(),*this));
191  }
192 
193  // the child groups of the current group
194  if(location == ChildrenGrps || location == AllChildrenGrps || location == AllGrps ) {
195  // get the number of groups
196  int groupCount = getGroupCount();
197  if (groupCount){
198  vector<int> ncids(groupCount);
199  int* numgrps=NULL;
200  // now get the id of each NcGroup and populate the ncGroups container.
201  ncCheck(nc_inq_grps(myId, numgrps,&ncids[0]),__FILE__,__LINE__);
202  for(int i=0; i<groupCount;i++){
203  NcGroup tmpGroup(ncids[i]);
204  ncGroups.insert(pair<const string,NcGroup>(tmpGroup.getName(),tmpGroup));
205  }
206  }
207  }
208 
209  // search in parent groups.
210  if(location == ParentsGrps || location == ParentsAndCurrentGrps || location == AllGrps ) {
211  NcGroup tmpGroup(*this);
212  if(!tmpGroup.isRootGroup()) {
213  while(1) {
214  const NcGroup parentGroup(tmpGroup.getParentGroup());
215  if(parentGroup.isNull()) break;
216  ncGroups.insert(pair<const string,NcGroup>(parentGroup.getName(),parentGroup));
217  tmpGroup=parentGroup;
218  }
219  }
220  }
221 
222  // search in child groups of the children
223  if(location == ChildrenOfChildrenGrps || location == AllChildrenGrps || location == AllGrps ) {
224  multimap<string,NcGroup>::iterator it;
225  multimap<string,NcGroup> groups(getGroups(ChildrenGrps));
226  for (it=groups.begin();it!=groups.end();it++) {
227  multimap<string,NcGroup> childGroups(it->second.getGroups(AllChildrenGrps));
228  ncGroups.insert(childGroups.begin(),childGroups.end());
229  }
230  }
231 
232  return ncGroups;
233 }
234 
235 // Get the named child NcGroup object.
236 NcGroup NcGroup::getGroup(const string& name,NcGroup::GroupLocation location) const{
237  if(isNull()) throw NcNullGrp("Attempt to invoke NcGroup::getGroup on a Null group",__FILE__,__LINE__);
238  multimap<string,NcGroup> ncGroups(getGroups(location));
239  pair<multimap<string,NcGroup>::iterator,multimap<string,NcGroup>::iterator> ret;
240  ret = ncGroups.equal_range(name);
241  if(ret.first == ret.second)
242  return NcGroup(); // null group is returned
243  else
244  return ret.first->second;
245 }
246 
247 
248 
249 // Get all NcGroup objects with a given name.
250 set<NcGroup> NcGroup::getGroups(const std::string& name,NcGroup::GroupLocation location) const {
251  if(isNull()) throw NcNullGrp("Attempt to invoke NcGroup::getGroups on a Null group",__FILE__,__LINE__);
252  // get the set of ncGroups in this group and above.
253  multimap<std::string,NcGroup> ncGroups(getGroups(location));
254  pair<multimap<string,NcGroup>::iterator,multimap<string,NcGroup>::iterator> ret;
255  multimap<string,NcGroup>::iterator it;
256  ret = ncGroups.equal_range(name);
257  set<NcGroup> tmpGroup;
258  for (it=ret.first; it!=ret.second; ++it) {
259  tmpGroup.insert(it->second);
260  }
261  return tmpGroup;
262 }
263 
264 // Add a new child NcGroup object.
265 NcGroup NcGroup::addGroup(const string& name) const {
266  if(isNull()) throw NcNullGrp("Attempt to invoke NcGroup::addGroup on a Null group",__FILE__,__LINE__);
267  int new_ncid;
268  ncCheck(nc_def_grp(myId,const_cast<char*> (name.c_str()),&new_ncid),__FILE__,__LINE__);
269  return NcGroup(new_ncid);
270 }
271 
272 
273 
274 // /////////////
275 // NcVar-related accessors
276 // /////////////
277 
278 // Get the number of NcVar objects in this group.
280 
281  // search in current group.
282  NcGroup tmpGroup(*this);
283  int nvars=0;
284  // search in current group
285  if((location == ParentsAndCurrent || location == ChildrenAndCurrent || location == Current || location ==All) && !tmpGroup.isNull()) {
286  ncCheck(nc_inq_nvars(tmpGroup.getId(), &nvars),__FILE__,__LINE__);
287  }
288 
289  // search recursively in all parent groups.
290  if(location == Parents || location == ParentsAndCurrent || location ==All) {
291  tmpGroup=getParentGroup();
292  while(!tmpGroup.isNull()) {
293  int nvarsp;
294  ncCheck(nc_inq_nvars(tmpGroup.getId(), &nvarsp),__FILE__,__LINE__);
295  nvars += nvarsp;
296  // continue loop with the parent.
297  tmpGroup=tmpGroup.getParentGroup();
298  }
299  }
300 
301  // search recursively in all child groups
302  if(location == ChildrenAndCurrent || location == Children || location == All) {
303  multimap<string,NcGroup>::iterator it;
304  multimap<string,NcGroup> groups(getGroups());
305  for (it=groups.begin();it!=groups.end();it++) {
306  nvars += it->second.getVarCount(ChildrenAndCurrent);
307  }
308  }
309  return nvars;
310 }
311 
312 // Get the collection of NcVar objects.
313 multimap<std::string,NcVar> NcGroup::getVars(NcGroup::Location location) const {
314 
315  // create a container to hold the NcVar's.
316  multimap<string,NcVar> ncVars;
317 
318  // search in current group.
319  NcGroup tmpGroup(*this);
320  if((location == ParentsAndCurrent || location == ChildrenAndCurrent || location == Current || location ==All) && !tmpGroup.isNull()) {
321  // get the number of variables.
322  int varCount = getVarCount();
323  if (varCount){
324  // now get the name of each NcVar object and populate the ncVars container.
325  int* nvars=NULL;
326  vector<int> varids(varCount);
327  ncCheck(nc_inq_varids(myId, nvars,&varids[0]),__FILE__,__LINE__);
328  for(int i=0; i<varCount;i++){
329  NcVar tmpVar(*this,varids[i]);
330  ncVars.insert(pair<const string,NcVar>(tmpVar.getName(),tmpVar));
331  }
332  }
333  }
334 
335 
336  // search recursively in all parent groups.
337  if(location == Parents || location == ParentsAndCurrent || location ==All) {
338  tmpGroup=getParentGroup();
339  while(!tmpGroup.isNull()) {
340  // get the number of variables
341  int varCount = tmpGroup.getVarCount();
342  if (varCount){
343  // now get the name of each NcVar object and populate the ncVars container.
344  int* nvars=NULL;
345  vector<int> varids(varCount);
346  ncCheck(nc_inq_varids(tmpGroup.getId(), nvars,&varids[0]),__FILE__,__LINE__);
347  for(int i=0; i<varCount;i++){
348  NcVar tmpVar(tmpGroup,varids[i]);
349  ncVars.insert(pair<const string,NcVar>(tmpVar.getName(),tmpVar));
350  }
351  }
352  // continue loop with the parent.
353  tmpGroup=tmpGroup.getParentGroup();
354  }
355  }
356 
357  // search recusively in all child groups.
358  if(location == ChildrenAndCurrent || location == Children || location == All ) {
359  multimap<string,NcGroup>::iterator it;
360  multimap<string,NcGroup> groups(getGroups());
361  for (it=groups.begin();it!=groups.end();it++) {
362  multimap<string,NcVar> vars=it->second.getVars(ChildrenAndCurrent);
363  ncVars.insert(vars.begin(),vars.end());
364  }
365  }
366 
367  return ncVars;
368 }
369 
370 
371 // Get all NcVar objects with a given name.
372 set<NcVar> NcGroup::getVars(const string& name,NcGroup::Location location) const {
373  // get the set of ncVars in this group and above.
374  multimap<std::string,NcVar> ncVars(getVars(location));
375  pair<multimap<string,NcVar>::iterator,multimap<string,NcVar>::iterator> ret;
376  multimap<string,NcVar>::iterator it;
377  ret = ncVars.equal_range(name);
378  set<NcVar> tmpVar;
379  for (it=ret.first; it!=ret.second; ++it) {
380  tmpVar.insert(it->second);
381  }
382  return tmpVar;
383 }
384 
385 
386 
387 // Get the named NcVar object.
388 NcVar NcGroup::getVar(const string& name,NcGroup::Location location) const {
389  multimap<std::string,NcVar> ncVars(getVars(location));
390  pair<multimap<string,NcVar>::iterator,multimap<string,NcVar>::iterator> ret;
391  ret = ncVars.equal_range(name);
392  if(ret.first == ret.second)
393  // no matching netCDF variable found so return null object.
394  return NcVar();
395  else
396  return ret.first->second;
397 }
398 
399 // Adds a new netCDF scalar variable.
400 NcVar NcGroup::addVar(const std::string& name, const NcType& ncType) const {
401  return NcGroup::addVar(name, ncType, std::vector<NcDim>());
402 }
403 
404 // Add a new netCDF variable.
405 NcVar NcGroup::addVar(const string& name, const string& typeName, const string& dimName) const {
406  ncCheckDefineMode(myId);
407 
408  // get an NcType object with the given type name.
409  NcType tmpType(getType(typeName,NcGroup::ParentsAndCurrent));
410  if(tmpType.isNull()) throw NcNullType("Attempt to invoke NcGroup::addVar failed: typeName must be defined in either the current group or a parent group",__FILE__,__LINE__);
411 
412  // get a NcDim object with the given dimension name
413  NcDim tmpDim(getDim(dimName,NcGroup::ParentsAndCurrent));
414  if(tmpDim.isNull()) throw NcNullDim("Attempt to invoke NcGroup::addVar failed: dimName must be defined in either the current group or a parent group",__FILE__,__LINE__);
415 
416  // finally define a new netCDF variable
417  int varId;
418  int dimId(tmpDim.getId());
419  ncCheck(nc_def_var(myId,name.c_str(),tmpType.getId(),1,&dimId,&varId),__FILE__,__LINE__);
420  // return an NcVar object for this new variable
421  return NcVar(*this,varId);
422 }
423 
424 
425 // Add a new netCDF variable.
426 NcVar NcGroup::addVar(const string& name, const NcType& ncType, const NcDim& ncDim) const {
427  ncCheckDefineMode(myId);
428 
429  // check NcType object is valid
430  if(ncType.isNull()) throw NcNullType("Attempt to invoke NcGroup::addVar with a Null NcType object",__FILE__,__LINE__);
432  if(tmpType.isNull()) throw NcNullType("Attempt to invoke NcGroup::addVar failed: NcType must be defined in either the current group or a parent group",__FILE__,__LINE__);
433 
434  // check NcDim object is valid
435  if(ncDim.isNull()) throw NcNullDim("Attempt to invoke NcGroup::addVar with a Null NcDim object",__FILE__,__LINE__);
437  if(tmpDim.isNull()) throw NcNullDim("Attempt to invoke NcGroup::addVar failed: NcDim must be defined in either the current group or a parent group",__FILE__,__LINE__);
438 
439  // finally define a new netCDF variable
440  int varId;
441  int dimId(tmpDim.getId());
442  ncCheck(nc_def_var(myId,name.c_str(),tmpType.getId(),1,&dimId,&varId),__FILE__,__LINE__);
443  // return an NcVar object for this new variable
444  return NcVar(*this,varId);
445 }
446 
447 
448 // Add a new netCDF multi-dimensional variable.
449 NcVar NcGroup::addVar(const string& name, const string& typeName, const vector<string>& dimNames) const {
450  ncCheckDefineMode(myId);
451 
452  // get an NcType object with the given name.
453  NcType tmpType(getType(typeName,NcGroup::ParentsAndCurrent));
454  if(tmpType.isNull()) throw NcNullType("Attempt to invoke NcGroup::addVar failed: typeName must be defined in either the current group or a parent group",__FILE__,__LINE__);
455 
456  // get a set of NcDim objects corresponding to the given dimension names.
457  vector<int> dimIds;
458  dimIds.reserve(dimNames.size());
459  for (size_t i=0; i<dimNames.size();i++){
460  NcDim tmpDim(getDim(dimNames[i],NcGroup::ParentsAndCurrent));
461  if(tmpDim.isNull()) throw NcNullDim("Attempt to invoke NcGroup::addVar failed: dimNames must be defined in either the current group or a parent group",__FILE__,__LINE__);
462  dimIds.push_back(tmpDim.getId());
463  }
464 
465  // finally define a new netCDF variable
466  int varId;
467  int *dimIdsPtr = dimIds.empty() ? 0 : &dimIds[0];
468  ncCheck(nc_def_var(myId,name.c_str(),tmpType.getId(),dimIds.size(), dimIdsPtr,&varId),__FILE__,__LINE__);
469  // return an NcVar object for this new variable
470  return NcVar(*this,varId);
471 }
472 
473 // Add a new netCDF multi-dimensional variable.
474 NcVar NcGroup::addVar(const string& name, const NcType& ncType, const vector<NcDim>& ncDimVector) const {
475  ncCheckDefineMode(myId);
476 
477  // check NcType object is valid
478  if(ncType.isNull()) throw NcNullType("Attempt to invoke NcGroup::addVar with a Null NcType object",__FILE__,__LINE__);
480  if(tmpType.isNull()) throw NcNullType("Attempt to invoke NcGroup::addVar failed: NcType must be defined in either the current group or a parent group",__FILE__,__LINE__);
481 
482  // check NcDim objects are valid
483  vector<NcDim>::const_iterator iter;
484  vector<int> dimIds;
485  dimIds.reserve(ncDimVector.size());
486  for (iter=ncDimVector.begin();iter < ncDimVector.end(); iter++) {
487  if(iter->isNull()) throw NcNullDim("Attempt to invoke NcGroup::addVar with a Null NcDim object",__FILE__,__LINE__);
488  NcDim tmpDim(getDim(iter->getName(),NcGroup::ParentsAndCurrent));
489  if(tmpDim.isNull()) throw NcNullDim("Attempt to invoke NcGroup::addVar failed: NcDim must be defined in either the current group or a parent group",__FILE__,__LINE__);
490  dimIds.push_back(tmpDim.getId());
491  }
492 
493  // finally define a new netCDF variable
494  int varId;
495  int *dimIdsPtr = dimIds.empty() ? 0 : &dimIds[0];
496  ncCheck(nc_def_var(myId,name.c_str(),tmpType.getId(),dimIds.size(), dimIdsPtr,&varId),__FILE__,__LINE__);
497  // return an NcVar object for this new variable
498  return NcVar(*this,varId);
499 }
500 
501 
502 // /////////////
503 // NcAtt-related methods
504 // /////////////
505 
506 // Get the number of group attributes.
508 
509  // search in current group.
510  NcGroup tmpGroup(*this);
511  int ngatts=0;
512  // search in current group
513  if((location == ParentsAndCurrent || location == ChildrenAndCurrent || location == Current || location ==All) && !tmpGroup.isNull()) {
514  ncCheck(nc_inq_natts(tmpGroup.getId(), &ngatts),__FILE__,__LINE__);
515  }
516 
517  // search recursively in all parent groups.
518  if(location == Parents || location == ParentsAndCurrent || location ==All) {
519  tmpGroup=getParentGroup();
520  while(!tmpGroup.isNull()) {
521  int ngattsp;
522  ncCheck(nc_inq_natts(tmpGroup.getId(), &ngattsp),__FILE__,__LINE__);
523  ngatts += ngattsp;
524  // continue loop with the parent.
525  tmpGroup=tmpGroup.getParentGroup();
526  }
527  }
528 
529  // search recursively in all child groups
530  if(location == ChildrenAndCurrent || location == Children || location == All) {
531  multimap<string,NcGroup>::iterator it;
532  multimap<string,NcGroup> groups(getGroups());
533  for (it=groups.begin();it!=groups.end();it++) {
534  ngatts += it->second.getAttCount(ChildrenAndCurrent);
535  }
536  }
537 
538  return ngatts;
539 }
540 
541 // Get the collection of NcGroupAtt objects.
542 multimap<std::string,NcGroupAtt> NcGroup::getAtts(NcGroup::Location location) const {
543 
544  // create a container to hold the NcAtt's.
545  multimap<string,NcGroupAtt> ncAtts;
546 
547  // search in current group.
548  NcGroup tmpGroup(*this);
549  if((location == ParentsAndCurrent || location == ChildrenAndCurrent || location == Current || location ==All) && !tmpGroup.isNull()) {
550  // get the number of attributes
551  int attCount = tmpGroup.getAttCount();
552  // now get the name of each NcAtt and populate the ncAtts container.
553  for(int i=0; i<attCount;i++){
554  char charName[NC_MAX_NAME+1];
555  ncCheck(nc_inq_attname(tmpGroup.getId(),NC_GLOBAL,i,charName),__FILE__,__LINE__);
556  NcGroupAtt tmpAtt(tmpGroup.getId(),i);
557  ncAtts.insert(pair<const string,NcGroupAtt>(string(charName),tmpAtt));
558  }
559  }
560 
561  // search recursively in all parent groups.
562  if(location == Parents || location == ParentsAndCurrent || location ==All) {
563  tmpGroup=getParentGroup();
564  while(!tmpGroup.isNull()) {
565  // get the number of attributes
566  int attCount = tmpGroup.getAttCount();
567  // now get the name of each NcAtt and populate the ncAtts container.
568  for(int i=0; i<attCount;i++){
569  char charName[NC_MAX_NAME+1];
570  ncCheck(nc_inq_attname(tmpGroup.getId(),NC_GLOBAL,i,charName),__FILE__,__LINE__);
571  NcGroupAtt tmpAtt(tmpGroup.getId(),i);
572  ncAtts.insert(pair<const string,NcGroupAtt>(string(charName),tmpAtt));
573  }
574  // continue loop with the parent.
575  tmpGroup=tmpGroup.getParentGroup();
576  }
577  }
578 
579  // search recusively in all child groups.
580  if(location == ChildrenAndCurrent || location == Children || location == All ) {
581  multimap<string,NcGroup>::iterator it;
582  multimap<string,NcGroup> groups(getGroups());
583  for (it=groups.begin();it!=groups.end();it++) {
584  multimap<string,NcGroupAtt> atts=it->second.getAtts(ChildrenAndCurrent);
585  ncAtts.insert(atts.begin(),atts.end());
586  }
587  }
588 
589  return ncAtts;
590 }
591 
592 // Get the named NcGroupAtt object.
593 NcGroupAtt NcGroup::getAtt(const std::string& name,NcGroup::Location location) const {
594  multimap<std::string,NcGroupAtt> ncAtts(getAtts(location));
595  pair<multimap<string,NcGroupAtt>::iterator,multimap<string,NcGroupAtt>::iterator> ret;
596  ret = ncAtts.equal_range(name);
597  if(ret.first == ret.second)
598  // no matching groupAttribute so return null object.
599  return NcGroupAtt();
600  else
601  return ret.first->second;
602 }
603 
604 // Get all NcGroupAtt objects with a given name.
605 set<NcGroupAtt> NcGroup::getAtts(const string& name,NcGroup::Location location) const {
606  // get the set of ncGroupAtts in this group and above.
607  multimap<std::string,NcGroupAtt> ncAtts(getAtts(location));
608  pair<multimap<string,NcGroupAtt>::iterator,multimap<string,NcGroupAtt>::iterator> ret;
609  multimap<string,NcGroupAtt>::iterator it;
610  ret = ncAtts.equal_range(name);
611  set<NcGroupAtt> tmpAtt;
612  for (it=ret.first; it!=ret.second; ++it) {
613  tmpAtt.insert(it->second);
614  }
615  return tmpAtt;
616 }
617 
618 
619 
620 
621 // Creates a new NetCDF group attribute or if already exisiting replaces it.
622 NcGroupAtt NcGroup::putAtt(const string& name, const string& dataValues) const {
623  ncCheckDefineMode(myId);
624  ncCheck(nc_put_att_text(myId,NC_GLOBAL,name.c_str(),dataValues.size(),dataValues.c_str()),__FILE__,__LINE__);
625  // finally instantiate this attribute and return
626  return getAtt(name);
627 }
628 
629 // Creates a new NetCDF group attribute or if already exisiting replaces it.
630 NcGroupAtt NcGroup::putAtt(const string& name, const NcType& type, size_t len, const unsigned char* dataValues) const {
631  ncCheckDefineMode(myId);
632  NcType::ncType typeClass(type.getTypeClass());
633  if(typeClass == NcType::nc_VLEN || typeClass == NcType::nc_OPAQUE || typeClass == NcType::nc_ENUM || typeClass == NcType::nc_COMPOUND)
634  ncCheck(nc_put_att(myId,NC_GLOBAL,name.c_str(),type.getId(),len,dataValues),__FILE__,__LINE__);
635  else
636  ncCheck(nc_put_att_uchar(myId,NC_GLOBAL,name.c_str(),type.getId(),len,dataValues),__FILE__,__LINE__);
637  // finally instantiate this attribute and return
638  return getAtt(name);
639 }
640 
641 
642 // Creates a new NetCDF group attribute or if already exisiting replaces it.
643 NcGroupAtt NcGroup::putAtt(const string& name, const NcType& type, size_t len, const signed char* dataValues) const {
644  ncCheckDefineMode(myId);
645  NcType::ncType typeClass(type.getTypeClass());
646  if(typeClass == NcType::nc_VLEN || typeClass == NcType::nc_OPAQUE || typeClass == NcType::nc_ENUM || typeClass == NcType::nc_COMPOUND)
647  ncCheck(nc_put_att(myId,NC_GLOBAL,name.c_str(),type.getId(),len,dataValues),__FILE__,__LINE__);
648  else
649  ncCheck(nc_put_att_schar(myId,NC_GLOBAL,name.c_str(),type.getId(),len,dataValues),__FILE__,__LINE__);
650  // finally instantiate this attribute and return
651  return getAtt(name);
652 }
653 
654 
655 // Creates a new NetCDF group attribute or if already exisiting replaces it.
656 NcGroupAtt NcGroup::putAtt(const string& name, const NcType& type, short datumValue) const {
657  ncCheckDefineMode(myId);
658  NcType::ncType typeClass(type.getTypeClass());
659  if(typeClass == NcType::nc_VLEN || typeClass == NcType::nc_OPAQUE || typeClass == NcType::nc_ENUM || typeClass == NcType::nc_COMPOUND)
660  ncCheck(nc_put_att(myId,NC_GLOBAL,name.c_str(),type.getId(),1,&datumValue),__FILE__,__LINE__);
661  else
662  ncCheck(nc_put_att_short(myId,NC_GLOBAL,name.c_str(),type.getId(),1,&datumValue),__FILE__,__LINE__);
663  // finally instantiate this attribute and return
664  return getAtt(name);
665 }
666 
667 
668 // Creates a new NetCDF group attribute or if already exisiting replaces it.
669 NcGroupAtt NcGroup::putAtt(const string& name, const NcType& type, int datumValue) const {
670  ncCheckDefineMode(myId);
671  NcType::ncType typeClass(type.getTypeClass());
672  if(typeClass == NcType::nc_VLEN || typeClass == NcType::nc_OPAQUE || typeClass == NcType::nc_ENUM || typeClass == NcType::nc_COMPOUND)
673  ncCheck(nc_put_att(myId,NC_GLOBAL,name.c_str(),type.getId(),1,&datumValue),__FILE__,__LINE__);
674  else
675  ncCheck(nc_put_att_int(myId,NC_GLOBAL,name.c_str(),type.getId(),1,&datumValue),__FILE__,__LINE__);
676  // finally instantiate this attribute and return
677  return getAtt(name);
678 }
679 
680 // Creates a new NetCDF group attribute or if already exisiting replaces it.
681 NcGroupAtt NcGroup::putAtt(const string& name, const NcType& type, long datumValue) const {
682  ncCheckDefineMode(myId);
683  NcType::ncType typeClass(type.getTypeClass());
684  if(typeClass == NcType::nc_VLEN || typeClass == NcType::nc_OPAQUE || typeClass == NcType::nc_ENUM || typeClass == NcType::nc_COMPOUND)
685  ncCheck(nc_put_att(myId,NC_GLOBAL,name.c_str(),type.getId(),1,&datumValue),__FILE__,__LINE__);
686  else
687  ncCheck(nc_put_att_long(myId,NC_GLOBAL,name.c_str(),type.getId(),1,&datumValue),__FILE__,__LINE__);
688  // finally instantiate this attribute and return
689  return getAtt(name);
690 }
691 
692 // Creates a new NetCDF group attribute or if already exisiting replaces it.
693 NcGroupAtt NcGroup::putAtt(const string& name, const NcType& type, float datumValue) const {
694  ncCheckDefineMode(myId);
695  NcType::ncType typeClass(type.getTypeClass());
696  if(typeClass == NcType::nc_VLEN || typeClass == NcType::nc_OPAQUE || typeClass == NcType::nc_ENUM || typeClass == NcType::nc_COMPOUND)
697  ncCheck(nc_put_att(myId,NC_GLOBAL,name.c_str(),type.getId(),1,&datumValue),__FILE__,__LINE__);
698  else
699  ncCheck(nc_put_att_float(myId,NC_GLOBAL,name.c_str(),type.getId(),1,&datumValue),__FILE__,__LINE__);
700  // finally instantiate this attribute and return
701  return getAtt(name);
702 }
703 
704 
705 // Creates a new NetCDF group attribute or if already exisiting replaces it.
706 NcGroupAtt NcGroup::putAtt(const string& name, const NcType& type, double datumValue) const {
707  ncCheckDefineMode(myId);
708  NcType::ncType typeClass(type.getTypeClass());
709  if(typeClass == NcType::nc_VLEN || typeClass == NcType::nc_OPAQUE || typeClass == NcType::nc_ENUM || typeClass == NcType::nc_COMPOUND)
710  ncCheck(nc_put_att(myId,NC_GLOBAL,name.c_str(),type.getId(),1,&datumValue),__FILE__,__LINE__);
711  else
712  ncCheck(nc_put_att_double(myId,NC_GLOBAL,name.c_str(),type.getId(),1,&datumValue),__FILE__,__LINE__);
713  // finally instantiate this attribute and return
714  return getAtt(name);
715 }
716 
717 
718 // Creates a new NetCDF group attribute or if already exisiting replaces it.
719 NcGroupAtt NcGroup::putAtt(const string& name, const NcType& type, unsigned short datumValue) const {
720  ncCheckDefineMode(myId);
721  NcType::ncType typeClass(type.getTypeClass());
722  if(typeClass == NcType::nc_VLEN || typeClass == NcType::nc_OPAQUE || typeClass == NcType::nc_ENUM || typeClass == NcType::nc_COMPOUND)
723  ncCheck(nc_put_att(myId,NC_GLOBAL,name.c_str(),type.getId(),1,&datumValue),__FILE__,__LINE__);
724  else
725  ncCheck(nc_put_att_ushort(myId,NC_GLOBAL,name.c_str(),type.getId(),1,&datumValue),__FILE__,__LINE__);
726  // finally instantiate this attribute and return
727  return getAtt(name);
728 }
729 
730 // Creates a new NetCDF group attribute or if already exisiting replaces it.
731 NcGroupAtt NcGroup::putAtt(const string& name, const NcType& type, unsigned int datumValue) const {
732  ncCheckDefineMode(myId);
733  NcType::ncType typeClass(type.getTypeClass());
734  if(typeClass == NcType::nc_VLEN || typeClass == NcType::nc_OPAQUE || typeClass == NcType::nc_ENUM || typeClass == NcType::nc_COMPOUND)
735  ncCheck(nc_put_att(myId,NC_GLOBAL,name.c_str(),type.getId(),1,&datumValue),__FILE__,__LINE__);
736  else
737  ncCheck(nc_put_att_uint(myId,NC_GLOBAL,name.c_str(),type.getId(),1,&datumValue),__FILE__,__LINE__);
738  // finally instantiate this attribute and return
739  return getAtt(name);
740 }
741 
742 // Creates a new NetCDF group attribute or if already exisiting replaces it.
743 NcGroupAtt NcGroup::putAtt(const string& name, const NcType& type, long long datumValue) const {
744  ncCheckDefineMode(myId);
745  NcType::ncType typeClass(type.getTypeClass());
746  if(typeClass == NcType::nc_VLEN || typeClass == NcType::nc_OPAQUE || typeClass == NcType::nc_ENUM || typeClass == NcType::nc_COMPOUND)
747  ncCheck(nc_put_att(myId,NC_GLOBAL,name.c_str(),type.getId(),1,&datumValue),__FILE__,__LINE__);
748  else
749  ncCheck(nc_put_att_longlong(myId,NC_GLOBAL,name.c_str(),type.getId(),1,&datumValue),__FILE__,__LINE__);
750  // finally instantiate this attribute and return
751  return getAtt(name);
752 }
753 
754 
755 // Creates a new NetCDF group attribute or if already exisiting replaces it.
756 NcGroupAtt NcGroup::putAtt(const string& name, const NcType& type, unsigned long long datumValue) const {
757  ncCheckDefineMode(myId);
758  NcType::ncType typeClass(type.getTypeClass());
759  if(typeClass == NcType::nc_VLEN || typeClass == NcType::nc_OPAQUE || typeClass == NcType::nc_ENUM || typeClass == NcType::nc_COMPOUND)
760  ncCheck(nc_put_att(myId,NC_GLOBAL,name.c_str(),type.getId(),1,&datumValue),__FILE__,__LINE__);
761  else
762  ncCheck(nc_put_att_ulonglong(myId,NC_GLOBAL,name.c_str(),type.getId(),1,&datumValue),__FILE__,__LINE__);
763  // finally instantiate this attribute and return
764  return getAtt(name);
765 }
766 
767 
768 // Creates a new NetCDF group attribute or if already exisiting replaces it.
769 NcGroupAtt NcGroup::putAtt(const string& name, const NcType& type, size_t len, const short* dataValues) const {
770  ncCheckDefineMode(myId);
771  NcType::ncType typeClass(type.getTypeClass());
772  if(typeClass == NcType::nc_VLEN || typeClass == NcType::nc_OPAQUE || typeClass == NcType::nc_ENUM || typeClass == NcType::nc_COMPOUND)
773  ncCheck(nc_put_att(myId,NC_GLOBAL,name.c_str(),type.getId(),len,dataValues),__FILE__,__LINE__);
774  else
775  ncCheck(nc_put_att_short(myId,NC_GLOBAL,name.c_str(),type.getId(),len,dataValues),__FILE__,__LINE__);
776  // finally instantiate this attribute and return
777  return getAtt(name);
778 }
779 
780 
781 // Creates a new NetCDF group attribute or if already exisiting replaces it.
782 NcGroupAtt NcGroup::putAtt(const string& name, const NcType& type, size_t len, const int* dataValues) const {
783  ncCheckDefineMode(myId);
784  NcType::ncType typeClass(type.getTypeClass());
785  if(typeClass == NcType::nc_VLEN || typeClass == NcType::nc_OPAQUE || typeClass == NcType::nc_ENUM || typeClass == NcType::nc_COMPOUND)
786  ncCheck(nc_put_att(myId,NC_GLOBAL,name.c_str(),type.getId(),len,dataValues),__FILE__,__LINE__);
787  else
788  ncCheck(nc_put_att_int(myId,NC_GLOBAL,name.c_str(),type.getId(),len,dataValues),__FILE__,__LINE__);
789  // finally instantiate this attribute and return
790  return getAtt(name);
791 }
792 
793 // Creates a new NetCDF group attribute or if already exisiting replaces it.
794 NcGroupAtt NcGroup::putAtt(const string& name, const NcType& type, size_t len, const long* dataValues) const {
795  ncCheckDefineMode(myId);
796  NcType::ncType typeClass(type.getTypeClass());
797  if(typeClass == NcType::nc_VLEN || typeClass == NcType::nc_OPAQUE || typeClass == NcType::nc_ENUM || typeClass == NcType::nc_COMPOUND)
798  ncCheck(nc_put_att(myId,NC_GLOBAL,name.c_str(),type.getId(),len,dataValues),__FILE__,__LINE__);
799  else
800  ncCheck(nc_put_att_long(myId,NC_GLOBAL,name.c_str(),type.getId(),len,dataValues),__FILE__,__LINE__);
801  // finally instantiate this attribute and return
802  return getAtt(name);
803 }
804 
805 // Creates a new NetCDF group attribute or if already exisiting replaces it.
806 NcGroupAtt NcGroup::putAtt(const string& name, const NcType& type, size_t len, const float* dataValues) const {
807  ncCheckDefineMode(myId);
808  NcType::ncType typeClass(type.getTypeClass());
809  if(typeClass == NcType::nc_VLEN || typeClass == NcType::nc_OPAQUE || typeClass == NcType::nc_ENUM || typeClass == NcType::nc_COMPOUND)
810  ncCheck(nc_put_att(myId,NC_GLOBAL,name.c_str(),type.getId(),len,dataValues),__FILE__,__LINE__);
811  else
812  ncCheck(nc_put_att_float(myId,NC_GLOBAL,name.c_str(),type.getId(),len,dataValues),__FILE__,__LINE__);
813  // finally instantiate this attribute and return
814  return getAtt(name);
815 }
816 
817 
818 // Creates a new NetCDF group attribute or if already exisiting replaces it.
819 NcGroupAtt NcGroup::putAtt(const string& name, const NcType& type, size_t len, const double* dataValues) const {
820  ncCheckDefineMode(myId);
821  NcType::ncType typeClass(type.getTypeClass());
822  if(typeClass == NcType::nc_VLEN || typeClass == NcType::nc_OPAQUE || typeClass == NcType::nc_ENUM || typeClass == NcType::nc_COMPOUND)
823  ncCheck(nc_put_att(myId,NC_GLOBAL,name.c_str(),type.getId(),len,dataValues),__FILE__,__LINE__);
824  else
825  ncCheck(nc_put_att_double(myId,NC_GLOBAL,name.c_str(),type.getId(),len,dataValues),__FILE__,__LINE__);
826  // finally instantiate this attribute and return
827  return getAtt(name);
828 }
829 
830 
831 // Creates a new NetCDF group attribute or if already exisiting replaces it.
832 NcGroupAtt NcGroup::putAtt(const string& name, const NcType& type, size_t len, const unsigned short* dataValues) const {
833  ncCheckDefineMode(myId);
834  NcType::ncType typeClass(type.getTypeClass());
835  if(typeClass == NcType::nc_VLEN || typeClass == NcType::nc_OPAQUE || typeClass == NcType::nc_ENUM || typeClass == NcType::nc_COMPOUND)
836  ncCheck(nc_put_att(myId,NC_GLOBAL,name.c_str(),type.getId(),len,dataValues),__FILE__,__LINE__);
837  else
838  ncCheck(nc_put_att_ushort(myId,NC_GLOBAL,name.c_str(),type.getId(),len,dataValues),__FILE__,__LINE__);
839  // finally instantiate this attribute and return
840  return getAtt(name);
841 }
842 
843 // Creates a new NetCDF group attribute or if already exisiting replaces it.
844 NcGroupAtt NcGroup::putAtt(const string& name, const NcType& type, size_t len, const unsigned int* dataValues) const {
845  ncCheckDefineMode(myId);
846  NcType::ncType typeClass(type.getTypeClass());
847  if(typeClass == NcType::nc_VLEN || typeClass == NcType::nc_OPAQUE || typeClass == NcType::nc_ENUM || typeClass == NcType::nc_COMPOUND)
848  ncCheck(nc_put_att(myId,NC_GLOBAL,name.c_str(),type.getId(),len,dataValues),__FILE__,__LINE__);
849  else
850  ncCheck(nc_put_att_uint(myId,NC_GLOBAL,name.c_str(),type.getId(),len,dataValues),__FILE__,__LINE__);
851  // finally instantiate this attribute and return
852  return getAtt(name);
853 }
854 
855 // Creates a new NetCDF group attribute or if already exisiting replaces it.
856 NcGroupAtt NcGroup::putAtt(const string& name, const NcType& type, size_t len, const long long* dataValues) const {
857  ncCheckDefineMode(myId);
858  NcType::ncType typeClass(type.getTypeClass());
859  if(typeClass == NcType::nc_VLEN || typeClass == NcType::nc_OPAQUE || typeClass == NcType::nc_ENUM || typeClass == NcType::nc_COMPOUND)
860  ncCheck(nc_put_att(myId,NC_GLOBAL,name.c_str(),type.getId(),len,dataValues),__FILE__,__LINE__);
861  else
862  ncCheck(nc_put_att_longlong(myId,NC_GLOBAL,name.c_str(),type.getId(),len,dataValues),__FILE__,__LINE__);
863  // finally instantiate this attribute and return
864  return getAtt(name);
865 }
866 
867 
868 // Creates a new NetCDF group attribute or if already exisiting replaces it.
869 NcGroupAtt NcGroup::putAtt(const string& name, const NcType& type, size_t len, const unsigned long long* dataValues) const {
870  ncCheckDefineMode(myId);
871  NcType::ncType typeClass(type.getTypeClass());
872  if(typeClass == NcType::nc_VLEN || typeClass == NcType::nc_OPAQUE || typeClass == NcType::nc_ENUM || typeClass == NcType::nc_COMPOUND)
873  ncCheck(nc_put_att(myId,NC_GLOBAL,name.c_str(),type.getId(),len,dataValues),__FILE__,__LINE__);
874  else
875  ncCheck(nc_put_att_ulonglong(myId,NC_GLOBAL,name.c_str(),type.getId(),len,dataValues),__FILE__,__LINE__);
876  // finally instantiate this attribute and return
877  return getAtt(name);
878 }
879 
880 
881 // Creates a new NetCDF group attribute or if already exisiting replaces it.
882 NcGroupAtt NcGroup::putAtt(const string& name, size_t len, const char** dataValues) const {
883  ncCheckDefineMode(myId);
884  ncCheck(nc_put_att_string(myId,NC_GLOBAL,name.c_str(),len,dataValues),__FILE__,__LINE__);
885  // finally instantiate this attribute and return
886  return getAtt(name);
887 }
888 
889 // Creates a new NetCDF group attribute or if already exisiting replaces it.
890  NcGroupAtt NcGroup::putAtt(const string& name, const NcType& type, size_t len, const void* dataValues) const {
891  ncCheckDefineMode(myId);
892  ncCheck(nc_put_att(myId,NC_GLOBAL,name.c_str(),type.getId(),len,dataValues),__FILE__,__LINE__);
893  // finally instantiate this attribute and return
894  return getAtt(name);
895 }
896 
897 
898 
899 // /////////////
900 // NcDim-related methods
901 // /////////////
902 
903 // Get the number of NcDim objects.
905  if(isNull()) throw NcNullGrp("Attempt to invoke NcGroup::getDimCount on a Null group",__FILE__,__LINE__);
906 
907  // intialize counter
908  int ndims=0;
909 
910  // search in current group
911  if(location == Current || location == ParentsAndCurrent || location == ChildrenAndCurrent || location == All ) {
912  int ndimsp;
913  ncCheck(nc_inq_ndims(getId(), &ndimsp),__FILE__,__LINE__);
914  ndims += ndimsp;
915  }
916 
917  // search in parent groups.
918  if(location == Parents || location == ParentsAndCurrent || location == All ) {
919  multimap<string,NcGroup>::iterator it;
920  multimap<string,NcGroup> groups(getGroups(ParentsGrps));
921  for (it=groups.begin();it!=groups.end();it++) {
922  ndims += it->second.getDimCount();
923  }
924  }
925 
926  // search in child groups.
927  if(location == Children || location == ChildrenAndCurrent || location == All ) {
928  multimap<string,NcGroup>::iterator it;
929  multimap<string,NcGroup> groups(getGroups(AllChildrenGrps));
930  for (it=groups.begin();it!=groups.end();it++) {
931  ndims += it->second.getDimCount();
932  }
933  }
934  return ndims;
935 }
936 
937 
938 // Get the set of NcDim objects.
939 multimap<string,NcDim> NcGroup::getDims(NcGroup::Location location) const {
940  if(isNull()) throw NcNullGrp("Attempt to invoke NcGroup::getDims on a Null group",__FILE__,__LINE__);
941  // create a container to hold the NcDim's.
942  multimap<string,NcDim> ncDims;
943 
944  // search in current group
945  if(location == Current || location == ParentsAndCurrent || location == ChildrenAndCurrent || location == All ) {
946  int dimCount = getDimCount();
947  if (dimCount){
948  vector<int> dimids(dimCount);
949  ncCheck(nc_inq_dimids(getId(), &dimCount, &dimids[0], 0),__FILE__,__LINE__);
950  // now get the name of each NcDim and populate the nDims container.
951  for(int i=0; i<dimCount;i++){
952  NcDim tmpDim(*this,dimids[i]);
953  ncDims.insert(pair<const string,NcDim>(tmpDim.getName(),tmpDim));
954  }
955  }
956  }
957 
958  // search in parent groups.
959  if(location == Parents || location == ParentsAndCurrent || location == All ) {
960  multimap<string,NcGroup>::iterator it;
961  multimap<string,NcGroup> groups(getGroups(ParentsGrps));
962  for (it=groups.begin();it!=groups.end();it++) {
963  multimap<string,NcDim> dimTmp(it->second.getDims());
964  ncDims.insert(dimTmp.begin(),dimTmp.end());
965  }
966  }
967 
968  // search in child groups (makes recursive calls).
969  if(location == Children || location == ChildrenAndCurrent || location == All ) {
970  multimap<string,NcGroup>::iterator it;
971  multimap<string,NcGroup> groups(getGroups(AllChildrenGrps));
972  for (it=groups.begin();it!=groups.end();it++) {
973  multimap<string,NcDim> dimTmp(it->second.getDims());
974  ncDims.insert(dimTmp.begin(),dimTmp.end());
975  }
976  }
977 
978  return ncDims;
979 }
980 
981 
982 
983 // Get the named NcDim object.
984 NcDim NcGroup::getDim(const string& name,NcGroup::Location location) const {
985  if(isNull()) throw NcNullGrp("Attempt to invoke NcGroup::getDim on a Null group",__FILE__,__LINE__);
986  multimap<string,NcDim> ncDims(getDims(location));
987  pair<multimap<string,NcDim>::iterator,multimap<string,NcDim>::iterator> ret;
988  ret = ncDims.equal_range(name);
989  if(ret.first == ret.second)
990  return NcDim(); // null group is returned
991  else
992  return ret.first->second;
993 }
994 
995 
996 // Get all NcDim objects with a given name.
997 set<NcDim> NcGroup::getDims(const string& name,NcGroup::Location location) const {
998  if(isNull()) throw NcNullGrp("Attempt to invoke NcGroup::getDims on a Null group",__FILE__,__LINE__);
999  // get the set of ncDims in this group and above.
1000  multimap<string,NcDim> ncDims(getDims(location));
1001  pair<multimap<string,NcDim>::iterator,multimap<string,NcDim>::iterator> ret;
1002  multimap<string,NcDim>::iterator it;
1003  ret = ncDims.equal_range(name);
1004  set<NcDim> tmpDim;
1005  for (it=ret.first; it!=ret.second; ++it) {
1006  tmpDim.insert(it->second);
1007  }
1008  return tmpDim;
1009 }
1010 
1011 // Add a new NcDim object.
1012 NcDim NcGroup::addDim(const string& name, size_t dimSize) const {
1013  ncCheckDefineMode(myId);
1014  if(isNull()) throw NcNullGrp("Attempt to invoke NcGroup::addDim on a Null group",__FILE__,__LINE__);
1015  int dimId;
1016  ncCheck(nc_def_dim(myId,name.c_str(),dimSize,&dimId),__FILE__,__LINE__);
1017  // finally return NcDim object for this new variable
1018  return NcDim(*this,dimId);
1019 }
1020 
1021 // Add a new NcDim object with unlimited size..
1022 NcDim NcGroup::addDim(const string& name) const {
1023  ncCheckDefineMode(myId);
1024  if(isNull()) throw NcNullGrp("Attempt to invoke NcGroup::addDim on a Null group",__FILE__,__LINE__);
1025  int dimId;
1026  ncCheck(nc_def_dim(myId,name.c_str(),NC_UNLIMITED,&dimId),__FILE__,__LINE__);
1027  // finally return NcDim object for this new variable
1028  return NcDim(*this,dimId);
1029 }
1030 
1031 
1032 
1033 
1034 
1035 // /////////////
1036 // type-object related methods
1037 // /////////////
1038 
1039 // Gets the number of type objects.
1041 
1042  if(isNull()) throw NcNullGrp("Attempt to invoke NcGroup::getTypeCount on a Null group",__FILE__,__LINE__);
1043 
1044  // intialize counter
1045  int ntypes=0;
1046 
1047  // search in current group
1048  if(location == Current || location == ParentsAndCurrent || location == ChildrenAndCurrent || location == All ) {
1049  int ntypesp;
1050  int* typeidsp=NULL;
1051  ncCheck(nc_inq_typeids(getId(), &ntypesp,typeidsp),__FILE__,__LINE__);
1052  ntypes+= ntypesp;
1053  }
1054 
1055  // search in parent groups.
1056  if(location == Parents || location == ParentsAndCurrent || location == All ) {
1057  multimap<string,NcGroup>::iterator it;
1058  multimap<string,NcGroup> groups(getGroups(ParentsGrps));
1059  for (it=groups.begin();it!=groups.end();it++) {
1060  ntypes += it->second.getTypeCount();
1061  }
1062  }
1063 
1064  // search in child groups.
1065  if(location == Children || location == ChildrenAndCurrent || location == All ) {
1066  multimap<string,NcGroup>::iterator it;
1067  multimap<string,NcGroup> groups(getGroups(AllChildrenGrps));
1068  for (it=groups.begin();it!=groups.end();it++) {
1069  ntypes += it->second.getTypeCount();
1070  }
1071  }
1072  return ntypes;
1073 }
1074 
1075 
1076 
1077 // Gets the number of type objects with a given enumeration type.
1079 
1080  if(isNull()) throw NcNullGrp("Attempt to invoke NcGroup::getTypeCount on a Null group",__FILE__,__LINE__);
1081 
1082  // intialize counter
1083  int ntypes=0;
1084 
1085  // search in current group
1086  if(location == Current || location == ParentsAndCurrent || location == ChildrenAndCurrent || location == All ) {
1087  int ntypesp;
1088  int* typeidsp=NULL;
1089  ncCheck(nc_inq_typeids(getId(), &ntypesp,typeidsp),__FILE__,__LINE__);
1090  if (ntypesp){
1091  vector<int> typeids(ntypesp);
1092  ncCheck(nc_inq_typeids(getId(), &ntypesp,&typeids[0]),__FILE__,__LINE__);
1093  for (int i=0; i<ntypesp;i++){
1094  NcType tmpType(*this,typeids[i]);
1095  if(tmpType.getTypeClass() == enumType) ntypes++;
1096  }
1097  }
1098  }
1099 
1100  // search in parent groups.
1101  if(location == Parents || location == ParentsAndCurrent || location == All ) {
1102  multimap<string,NcGroup>::iterator it;
1103  multimap<string,NcGroup> groups(getGroups(ParentsGrps));
1104  for (it=groups.begin();it!=groups.end();it++) {
1105  ntypes += it->second.getTypeCount(enumType);
1106  }
1107  }
1108 
1109  // search in child groups.
1110  if(location == Children || location == ChildrenAndCurrent || location == All ) {
1111  multimap<string,NcGroup>::iterator it;
1112  multimap<string,NcGroup> groups(getGroups(AllChildrenGrps));
1113  for (it=groups.begin();it!=groups.end();it++) {
1114  ntypes += it->second.getTypeCount(enumType);
1115  }
1116  }
1117  return ntypes;
1118 }
1119 
1120 
1121 // Gets the collection of NcType objects.
1122 multimap<string,NcType> NcGroup::getTypes(NcGroup::Location location) const {
1123  if(isNull()) throw NcNullGrp("Attempt to invoke NcGroup::getTypes on a Null group",__FILE__,__LINE__);
1124  // create a container to hold the NcType's.
1125  multimap<string,NcType> ncTypes;
1126 
1127  // search in current group
1128  if(location == Current || location == ParentsAndCurrent || location == ChildrenAndCurrent || location == All ) {
1129  int typeCount = getTypeCount();
1130  if (typeCount){
1131  vector<int> typeids(typeCount);
1132  ncCheck(nc_inq_typeids(getId(), &typeCount,&typeids[0]),__FILE__,__LINE__);
1133  // now get the name of each NcType and populate the nTypes container.
1134  for(int i=0; i<typeCount;i++){
1135  NcType tmpType(*this,typeids[i]);
1136  ncTypes.insert(pair<const string,NcType>(tmpType.getName(),tmpType));
1137  }
1138  }
1139  }
1140 
1141  // search in parent groups.
1142  if(location == Parents || location == ParentsAndCurrent || location == All ) {
1143  multimap<string,NcGroup>::iterator it;
1144  multimap<string,NcGroup> groups(getGroups(ParentsGrps));
1145  for (it=groups.begin();it!=groups.end();it++) {
1146  multimap<string,NcType> typeTmp(it->second.getTypes());
1147  ncTypes.insert(typeTmp.begin(),typeTmp.end());
1148  }
1149  }
1150 
1151  // search in child groups (makes recursive calls).
1152  if(location == Children || location == ChildrenAndCurrent || location == All ) {
1153  multimap<string,NcGroup>::iterator it;
1154  multimap<string,NcGroup> groups(getGroups(AllChildrenGrps));
1155  for (it=groups.begin();it!=groups.end();it++) {
1156  multimap<string,NcType> typeTmp(it->second.getTypes());
1157  ncTypes.insert(typeTmp.begin(),typeTmp.end());
1158  }
1159  }
1160 
1161  return ncTypes;
1162 }
1163 
1164 
1165 // Gets the collection of NcType objects with a given name.
1166 set<NcType> NcGroup::getTypes(const string& name, NcGroup::Location location) const {
1167  if(isNull()) throw NcNullGrp("Attempt to invoke NcGroup::getTypes on a Null group",__FILE__,__LINE__);
1168  // iterator for the multimap container.
1169  multimap<string,NcType>::iterator it;
1170  // return argument of equal_range: iterators to lower and upper bounds of the range.
1171  pair<multimap<string,NcType>::iterator,multimap<string,NcType>::iterator> ret;
1172  // get the entire collection of types.
1173  multimap<string,NcType> types(getTypes(location));
1174  // define STL set object to hold the result
1175  set<NcType> tmpType;
1176  // get the set of NcType objects with a given name
1177  ret=types.equal_range(name);
1178  for (it=ret.first;it!=ret.second;it++) {
1179  tmpType.insert(it->second);
1180  }
1181  return tmpType;
1182 }
1183 
1184 
1185 // Gets the collection of NcType objects with a given data type.
1186 set<NcType> NcGroup::getTypes(NcType::ncType enumType, NcGroup::Location location) const {
1187  if(isNull()) throw NcNullGrp("Attempt to invoke NcGroup::getTypes on a Null group",__FILE__,__LINE__);
1188  // iterator for the multimap container.
1189  multimap<string,NcType>::iterator it;
1190  // get the entire collection of types.
1191  multimap<string,NcType> types(getTypes(location));
1192  // define STL set object to hold the result
1193  set<NcType> tmpType;
1194  // get the set of NcType objects with a given data type
1195  for (it=types.begin();it!=types.end();it++) {
1196  if(it->second.getTypeClass() == enumType) {
1197  tmpType.insert(it->second);
1198  }
1199  }
1200  return(tmpType);
1201 }
1202 
1203 
1204 // Gets the collection of NcType objects with a given name and data type.
1205 set<NcType> NcGroup::getTypes(const string& name, NcType::ncType enumType, NcGroup::Location location) const {
1206  if(isNull()) throw NcNullGrp("Attempt to invoke NcGroup::getTypes on a Null group",__FILE__,__LINE__);
1207  // iterator for the multimap container.
1208  multimap<string,NcType>::iterator it;
1209  // return argument of equal_range: iterators to lower and upper bounds of the range.
1210  pair<multimap<string,NcType>::iterator,multimap<string,NcType>::iterator> ret;
1211  // get the entire collection of types.
1212  multimap<string,NcType> types(getTypes(location));
1213  // define STL set object to hold the result
1214  set<NcType> tmpType;
1215  // get the set of NcType objects with a given name
1216  ret=types.equal_range(name);
1217  for (it=ret.first;it!=ret.second;it++) {
1218  if((*it).second.getTypeClass() == enumType) {
1219  tmpType.insert(it->second);
1220  }
1221  }
1222  return(tmpType);
1223 }
1224 
1225 
1226 // Gets the NcType object with a given name.
1227 NcType NcGroup::getType(const string& name, NcGroup::Location location) const {
1228  if(isNull()) throw NcNullGrp("Attempt to invoke NcGroup::getType on a Null group",__FILE__,__LINE__);
1229  if(name == "byte" ) return ncByte;
1230  if(name == "ubyte" ) return ncUbyte;
1231  if(name == "char" ) return ncChar;
1232  if(name == "short" ) return ncShort;
1233  if(name == "ushort" ) return ncUshort;
1234  if(name == "int" ) return ncInt;
1235  if(name == "uint" ) return ncUint;
1236  if(name == "int64" ) return ncInt64;
1237  if(name == "uint64" ) return ncUint64;
1238  if(name == "float" ) return ncFloat;
1239  if(name == "double" ) return ncDouble;
1240  if(name == "string" ) return ncString;
1241 
1242  // this is a user defined type
1243  // iterator for the multimap container.
1244  multimap<string,NcType>::iterator it;
1245  // return argument of equal_range: iterators to lower and upper bounds of the range.
1246  pair<multimap<string,NcType>::iterator,multimap<string,NcType>::iterator> ret;
1247  // get the entire collection of types.
1248  multimap<string,NcType> types(getTypes(location));
1249  // define STL set object to hold the result
1250  set<NcType> tmpType;
1251  // get the set of NcType objects with a given name
1252  ret=types.equal_range(name);
1253  if(ret.first == ret.second)
1254  return NcType();
1255  else
1256  return ret.first->second;
1257 }
1258 
1259 
1260 // Adds a new netCDF Enum type.
1261 NcEnumType NcGroup::addEnumType(const string& name,NcEnumType::ncEnumType baseType) const {
1262  ncCheckDefineMode(myId);
1263  nc_type typeId;
1264  ncCheck(nc_def_enum(myId, baseType, name.c_str(), &typeId),__FILE__,__LINE__);
1265  NcEnumType ncTypeTmp(*this,name);
1266  return ncTypeTmp;
1267 }
1268 
1269 
1270 // Adds a new netCDF Vlen type.
1271 NcVlenType NcGroup::addVlenType(const string& name,NcType& baseType) const {
1272  ncCheckDefineMode(myId);
1273  nc_type typeId;
1274  ncCheck(nc_def_vlen(myId, const_cast<char*>(name.c_str()),baseType.getId(),&typeId),__FILE__,__LINE__);
1275  NcVlenType ncTypeTmp(*this,name);
1276  return ncTypeTmp;
1277 }
1278 
1279 
1280 // Adds a new netCDF Opaque type.
1281 NcOpaqueType NcGroup::addOpaqueType(const string& name, size_t size) const {
1282  ncCheckDefineMode(myId);
1283  nc_type typeId;
1284  ncCheck(nc_def_opaque(myId, size,const_cast<char*>(name.c_str()), &typeId),__FILE__,__LINE__);
1285  NcOpaqueType ncTypeTmp(*this,name);
1286  return ncTypeTmp;
1287 }
1288 
1289 // Adds a new netCDF UserDefined type.
1290 NcCompoundType NcGroup::addCompoundType(const string& name, size_t size) const {
1291  ncCheckDefineMode(myId);
1292  nc_type typeId;
1293  ncCheck(nc_def_compound(myId, size,const_cast<char*>(name.c_str()),&typeId),__FILE__,__LINE__);
1294  NcCompoundType ncTypeTmp(*this,name);
1295  return ncTypeTmp;
1296 }
1297 
1298 
1299 // Get the collection of coordinate variables.
1300 map<string,NcGroup> NcGroup::getCoordVars(NcGroup::Location location) const {
1301  map<string,NcGroup> coordVars;
1302 
1303  // search in current group and parent groups.
1304  NcGroup tmpGroup(*this);
1305  multimap<string,NcDim>::iterator itD;
1306  multimap<string,NcVar>::iterator itV;
1307  while(1) {
1308  // get the collection of NcDim objects defined in this group.
1309  multimap<string,NcDim> dimTmp(tmpGroup.getDims());
1310  multimap<string,NcVar> varTmp(tmpGroup.getVars());
1311  for (itD=dimTmp.begin();itD!=dimTmp.end();itD++) {
1312  string coordName(itD->first);
1313  itV = varTmp.find(coordName);
1314  if(itV != varTmp.end()) {
1315  coordVars.insert(pair<const string,NcGroup>(string(coordName),tmpGroup));
1316  }
1317  }
1318  if(location != ParentsAndCurrent || location != All || tmpGroup.isRootGroup()) {
1319  break;
1320  }
1321  // continue loop with the parent.
1322  tmpGroup=tmpGroup.getParentGroup();
1323  }
1324 
1325  // search in child groups (makes recursive calls).
1326  if(location == ChildrenAndCurrent || location == All ) {
1327  multimap<string,NcGroup>::iterator it;
1328  multimap<string,NcGroup> groups(getGroups());
1329  for (it=groups.begin();it!=groups.end();it++) {
1330  map<string,NcGroup> coordVarsTmp=getCoordVars(ChildrenAndCurrent);
1331  coordVars.insert(coordVarsTmp.begin(),coordVarsTmp.end());
1332  }
1333  }
1334 
1335  return coordVars;
1336 }
1337 
1338 // Get the NcDim and NcVar object pair for a named coordinate variables.
1339 void NcGroup::getCoordVar(string& coordVarName, NcDim& ncDim, NcVar& ncVar, NcGroup::Location location) const {
1340 
1341  // search in current group and parent groups.
1342  multimap<string,NcDim>::iterator itD;
1343  NcGroup tmpGroup(*this);
1344  multimap<string,NcVar>::iterator itV;
1345  while(1) {
1346  // get the collection of NcDim objects defined in this group.
1347  multimap<string,NcDim> dimTmp(tmpGroup.getDims());
1348  multimap<string,NcVar> varTmp(tmpGroup.getVars());
1349  itD=dimTmp.find(coordVarName);
1350  itV=varTmp.find(coordVarName);
1351  if(itD != dimTmp.end() && itV != varTmp.end()) {
1352  ncDim=itD->second;
1353  ncVar=itV->second;
1354  return;
1355  }
1356  if(location != ParentsAndCurrent || location != All || tmpGroup.isRootGroup()) {
1357  break;
1358  }
1359  // continue loop with the parent.
1360  tmpGroup=tmpGroup.getParentGroup();
1361  }
1362 
1363  // search in child groups (makes recursive calls).
1364  if(location == ChildrenAndCurrent || location == All ) {
1365  multimap<string,NcGroup>::iterator it;
1366  multimap<string,NcGroup> groups(getGroups());
1367  for (it=groups.begin();it!=groups.end();it++) {
1368  getCoordVar(coordVarName,ncDim,ncVar,ChildrenAndCurrent);
1369  if(!ncDim.isNull()) break;
1370  }
1371  }
1372 
1373  if(ncDim.isNull()) {
1374  // return null objects as no coordinates variables were obtained.
1375  NcDim dimTmp;
1376  NcVar varTmp;
1377  ncDim=dimTmp;
1378  ncVar=varTmp;
1379  return;
1380  }
1381 
1382 }
NcGroupAtt getAtt(const std::string &name, NcGroup::Location location=Current) const
Gets the named NcGroupAtt object.
Definition: ncGroup.cpp:593
Thrown if the requested operation is on a NULL type.
Definition: ncException.h:405
const int getId() const
The netCDF Id of this dimension.
Definition: ncDim.h:47
GroupLocation
The enumeration list contains the options for selecting groups (used for returned set of NcGroup obje...
Definition: ncGroup.h:35
Base class inherited by NcOpaque, NcVlen, NcCompound and NcEnum classes.
Definition: ncType.h:14
NcUint64 ncUint64
A global instance of the NcUint64 class within the netCDF namespace.
Definition: ncUint64.cpp:7
bool isNull() const
Returns true if this object is null (i.e.
Definition: ncGroup.h:158
Thrown if cannot return a netCDF group.
Definition: ncException.h:383
bool operator==(const NcGroup &rhs) const
equivalence operator
Definition: ncGroup.cpp:77
Select from set of all children of the current group and beneath.
Definition: ncGroup.h:40
int getDimCount(NcGroup::Location location=Current) const
Gets the number of NcDim objects.
Definition: ncGroup.cpp:904
"NcOpaque type"
Definition: ncType.h:40
NcGroup getParentGroup() const
Gets the parent group.
Definition: ncGroup.cpp:125
C++ API for netCDF4.
Definition: ncAtt.h:9
bool nullObject
assignment operator
Definition: ncGroup.h:570
std::multimap< std::string, NcGroup > getGroups(NcGroup::GroupLocation location=ChildrenGrps) const
Gets the collection of NcGroup objects.
Definition: ncGroup.cpp:183
Select from contents of current group.
Definition: ncGroup.h:50
Location
The enumeration list contains the options for selecting groups.
Definition: ncGroup.h:48
NcGroupAtt putAtt(const std::string &name, size_t len, const char **dataValues) const
This is an overloaded member function, provided for convenience. It differs from the above function o...
Select from contents of parents groups.
Definition: ncGroup.h:51
Select from the set of children in the current group.
Definition: ncGroup.h:37
Thrown if the requested operation is on a NULL group.
Definition: ncException.h:394
bool isNull() const
Returns true if this object is null (i.e.
Definition: ncDim.h:62
NcByte ncByte
A global instance of the NcByte class within the netCDF namespace.
Definition: ncByte.cpp:7
NcType getType(const std::string &name, NcGroup::Location location=Current) const
Gets the NcType object with a given name.
Definition: ncGroup.cpp:1227
int getAttCount(NcGroup::Location location=Current) const
Gets the number of group attributes.
Definition: ncGroup.cpp:507
"NcCompound type"
Definition: ncType.h:42
Class represents a netCDF compound type.
int getId() const
Gets the group id.
Definition: ncGroup.cpp:141
Class represents a netCDF enum type.
Definition: ncEnumType.h:15
Select from set of parent groups(includes the current group).
Definition: ncGroup.h:41
"NcVlen type"
Definition: ncType.h:39
NcVlenType addVlenType(const std::string &name, NcType &basetype) const
Adds a new netCDF Vlen type.
Definition: ncGroup.cpp:1271
std::string getName(bool fullName=false) const
Gets the group name.
Definition: ncGroup.cpp:97
Class represents a netCDF VLEN type.
Definition: ncVlenType.h:14
NcEnumType addEnumType(const std::string &name, NcEnumType::ncEnumType basetype) const
Adds a new netCDF enum type.
Definition: ncGroup.cpp:1261
NcFloat ncFloat
A global instance of the NcFloat class within the netCDF namespace.
Definition: ncFloat.cpp:7
Class represents a netCDF group.
Definition: ncGroup.h:27
void getCoordVar(std::string &coordVarName, NcDim &ncDim, NcVar &ncVar, NcGroup::Location location=Current) const
Gets the NcDim and NcVar object pair for a named coordinate variable.
Definition: ncGroup.cpp:1339
int getGroupCount(NcGroup::GroupLocation location=ChildrenGrps) const
Gets the number of NcGroup objects.
Definition: ncGroup.cpp:147
Class represents a netCDF group attribute.
Definition: ncGroupAtt.h:12
ncType
List of netCDF types that can be represented.
Definition: ncType.h:25
Exception classes.
Definition: ncException.h:15
NcUint ncUint
A global instance of the NcUint class within the netCDF namespace.
Definition: ncUint.cpp:7
Select from set of parent groups, current groups and all the children beneath.
Definition: ncGroup.h:42
NcChar ncChar
A global instance of the NcChar class within the netCDF namespace.
Definition: ncChar.cpp:7
NcGroup getGroup(const std::string &name, NcGroup::GroupLocation location=ChildrenGrps) const
Gets the named child NcGroup object.
Definition: ncGroup.cpp:236
bool isNull() const
Returns true if this object is null (i.e.
Definition: ncType.h:133
Thrown if the requested operation is on a NULL dimension.
Definition: ncException.h:416
NcGroup & operator=(const NcGroup &rhs)
assignment operator
Definition: ncGroup.cpp:62
std::string getName() const
The name of this type.
Definition: ncType.cpp:94
NcVar addVar(const std::string &name, const NcType &ncType) const
Adds a new netCDF scalar variable.
Definition: ncGroup.cpp:400
std::multimap< std::string, NcDim > getDims(NcGroup::Location location=Current) const
Gets the collection of NcDim objects.
Definition: ncGroup.cpp:939
Select from contents of current, parents and child groups.
Definition: ncGroup.h:55
nc_type getId() const
The netCDF Id of this type.
Definition: ncType.h:88
NcDouble ncDouble
A global instance of the NcDouble class within the netCDF namespace.
Definition: ncDouble.cpp:7
Class represents a netCDF dimension.
Definition: ncDim.h:13
NcGroup addGroup(const std::string &name) const
Adds a new child netCDF group object.
Definition: ncGroup.cpp:265
Select from contents of current and parents groups.
Definition: ncGroup.h:53
NcDim getDim(const std::string &name, NcGroup::Location location=Current) const
Gets the named NcDim object.
Definition: ncGroup.cpp:984
std::multimap< std::string, NcType > getTypes(NcGroup::Location location=Current) const
Gets the collection of NcType objects.
Definition: ncGroup.cpp:1122
Select from contents of children groups.
Definition: ncGroup.h:52
std::multimap< std::string, NcGroupAtt > getAtts(NcGroup::Location location=Current) const
Gets the collection of NcGroupAtt objects.
Definition: ncGroup.cpp:542
void ncCheck(int retCode, const char *file, int line)
Function checks error code and if necessary throws an exception.
Definition: ncCheck.cpp:11
NcShort ncShort
A global instance of the NcShort class within the netCDF namespace.
Definition: ncShort.cpp:7
bool isRootGroup() const
Returns true if this is the root group, otherwise returns false.
Definition: ncGroup.cpp:119
std::string getName() const
Name of this NcVar object.
Definition: ncVar.cpp:528
void ncCheckDefineMode(int ncid)
Function checks if the file (group) is in define mode.
Definition: ncCheck.cpp:83
NcDim addDim(const std::string &name, size_t dimSize) const
Adds a new netCDF dimension.
int getVarCount(NcGroup::Location location=Current) const
Gets the number of NcVar objects in this group.
Definition: ncGroup.cpp:279
Select from contents of current and child groups.
Definition: ncGroup.h:54
std::multimap< std::string, NcVar > getVars(NcGroup::Location location=Current) const
Get the collection of NcVar objects.
Definition: ncGroup.cpp:313
ncEnumType
List of NetCDF-4 Enumeration types.
Definition: ncEnumType.h:20
"NcEnum type"
Definition: ncType.h:41
NcVar getVar(const std::string &name, NcGroup::Location location=Current) const
Gets the named NcVar object.
Definition: ncGroup.cpp:388
NcString ncString
A global instance of the NcString class within the netCDF namespace.
Definition: ncString.cpp:7
Select from set of parent groups (excludes the current group).
Definition: ncGroup.h:38
NcCompoundType addCompoundType(const std::string &name, size_t size) const
Adds a new netCDF UserDefined type.
Definition: ncGroup.cpp:1290
Class represents a netCDF opaque type.
Definition: ncOpaqueType.h:14
int getTypeCount(NcGroup::Location location=Current) const
Gets the number of type objects.
Definition: ncGroup.cpp:1040
Class represents a netCDF variable.
Definition: ncVar.h:33
std::map< std::string, NcGroup > getCoordVars(NcGroup::Location location=Current) const
Gets a collection of coordinate variables.
Definition: ncGroup.cpp:1300
NcGroup()
Constructor generates a null object.
Definition: ncGroup.cpp:49
NcOpaqueType addOpaqueType(const std::string &name, size_t size) const
Adds a new netCDF Opaque type.
Definition: ncGroup.cpp:1281
const std::string getName() const
The name of this dimension.
Definition: ncDim.cpp:106
NcInt ncInt
A global instance of the NcInt class within the netCDF namespace.
Definition: ncInt.cpp:7
ncType getTypeClass() const
The type class returned as enumeration type.
Definition: ncType.cpp:116
bool operator!=(const NcGroup &rhs) const
!= operator
Definition: ncGroup.cpp:86
NcUbyte ncUbyte
A global instance of the NcUbyte class within the netCDF namespace.
Definition: ncUbyte.cpp:7
NcInt64 ncInt64
A global instance of the NcInt64 class within the netCDF namespace.
Definition: ncInt64.cpp:7
Select from set of all children of children in the current group.
Definition: ncGroup.h:39

Return to the Main Unidata NetCDF page.
Generated on Fri Nov 11 2016 15:28:29 for NetCDF-C++. NetCDF is a Unidata library.