source: XIOS/trunk/src/declare_ref_func.hpp @ 770

Last change on this file since 770 was 770, checked in by rlacroix, 8 years ago

Field: Handle more correctly the output name for the fields with a field_ref.

If the field has an explicitly defined name (which might be inherited) then it is used as the output name.
If no name was defined but an id was set, the id is used as the output name.
If no name was defined and the id was automatically generated, the id of the field directly referenced is used as the output name.

File size: 7.2 KB
Line 
1/*!
2   \file declare_ref_func.hpp
3   \author Ha NGUYEN
4   \date 02 Dec 2014
5   \since 02 Dec 2014
6
7   \brief Macros to add functions used to solve references in class CDomain, CAxis and CField
8 */
9#ifndef __XIOS_DECLARE_REF_FUNC_HPP__
10#define __XIOS_DECLARE_REF_FUNC_HPP__
11
12// Declarations
13
14#define DECLARE_REF_FUNC(type, name_)                       \
15public:                                                     \
16  bool hasDirect##type##Reference(void) const;              \
17  C##type* getDirect##type##Reference(void) const;          \
18  C##type* getBase##type##Reference(void) const;            \
19  void removeRefInheritance();                              \
20  const StdString& getBase##type##Id(void) const;           \
21  void solveRefInheritance(bool apply = true);              \
22  void solveBaseReference(void);                            \
23  const StdString& get##type##OutputName(void) const;       \
24                                                            \
25private:                                                    \
26  C##type* baseRefObject;                                   \
27
28// Definitions
29
30#define DEFINE_REF_FUNC(type, name_)                                   \
31void C##type::solveRefInheritance(bool apply)                          \
32{                                                                      \
33  std::set<C##type*> refObjects;                                       \
34  C##type* refer_ptr = this;                                           \
35                                                                       \
36  while (refer_ptr->hasDirect##type##Reference())                      \
37  {                                                                    \
38    refObjects.insert(refer_ptr);                                      \
39                                                                       \
40    refer_ptr = refer_ptr->getDirect##type##Reference();               \
41                                                                       \
42    if (refObjects.end() != refObjects.find(refer_ptr))                \
43    {                                                                  \
44      ERROR("void C" #type "::solveRefInheritance(bool apply)",        \
45            << "Circular dependency stopped for " #name_ " object "    \
46            << "with id = \"" << refer_ptr->getId() << "\".");         \
47    }                                                                  \
48                                                                       \
49    SuperClassAttribute::setAttributes(refer_ptr, apply);              \
50  }                                                                    \
51}                                                                      \
52                                                                       \
53void C##type::removeRefInheritance()                                   \
54{                                                                      \
55  if (!this->name_##_ref.isEmpty())                                    \
56    this->name_##_ref.reset();                                         \
57}                                                                      \
58                                                                       \
59void C##type::solveBaseReference(void)                                 \
60{                                                                      \
61  std::set<C##type*> refObjects;                                       \
62  baseRefObject = C##type::get(this);                                  \
63                                                                       \
64  while (baseRefObject->hasDirect##type##Reference())                  \
65  {                                                                    \
66    refObjects.insert(baseRefObject);                                  \
67                                                                       \
68    baseRefObject = baseRefObject->getDirect##type##Reference();       \
69                                                                       \
70    if (refObjects.end() != refObjects.find(baseRefObject))            \
71    {                                                                  \
72      ERROR("void C" #type "::solveBaseReference(void)",               \
73            << "Circular dependency stopped for " #name_ " object "    \
74            << "with id = \"" << baseRefObject->getId() << "\".");     \
75    }                                                                  \
76  }                                                                    \
77}                                                                      \
78                                                                       \
79C##type* C##type::getDirect##type##Reference(void) const               \
80{                                                                      \
81  if (this->name_##_ref.isEmpty())                                     \
82    return this->getBase##type##Reference();                           \
83                                                                       \
84  if (!C##type::has(this->name_##_ref))                                \
85    ERROR("C" #type "* C" #type "::getDirect" #type "Reference(void)", \
86          << this->name_##_ref                                         \
87          << " refers to an unknown " #name_ " id.");                  \
88                                                                       \
89  return C##type::get(this->name_##_ref);                              \
90}                                                                      \
91                                                                       \
92C##type* C##type::getBase##type##Reference(void) const                 \
93{                                                                      \
94  return baseRefObject;                                                \
95}                                                                      \
96                                                                       \
97const StdString& C##type::getBase##type##Id(void) const                \
98{                                                                      \
99  return this->getBase##type##Reference()->getId();                    \
100}                                                                      \
101bool C##type::hasDirect##type##Reference(void) const                   \
102{                                                                      \
103  return !this->name_##_ref.isEmpty();                                 \
104}                                                                      \
105                                                                       \
106const StdString& C##type::get##type##OutputName(void) const            \
107{                                                                      \
108  if (!this->name.isEmpty())                                           \
109    return this->name;                                                 \
110  else if (hasAutoGeneratedId() && hasDirect##type##Reference())       \
111    return this->name_##_ref;                                          \
112  else                                                                 \
113    return getId();                                                    \
114}                                                                      \
115
116#endif // __XIOS_DECLARE_REF_FUNC_HPP__
Note: See TracBrowser for help on using the repository browser.