// // ******************************************************************** // * License and Disclaimer * // * * // * The Geant4 software is copyright of the Copyright Holders of * // * the Geant4 Collaboration. It is provided under the terms and * // * conditions of the Geant4 Software License, included in the file * // * LICENSE and available at http://cern.ch/geant4/license . These * // * include a list of copyright holders. * // * * // * Neither the authors of this software system, nor their employing * // * institutes,nor the agencies providing financial support for this * // * work make any representation or warranty, express or implied, * // * regarding this software system or assume any liability for its * // * use. Please see the license in the file LICENSE and URL above * // * for the full disclaimer and the limitation of liability. * // * * // * This code implementation is the result of the scientific and * // * technical work of the GEANT4 collaboration. * // * By using, copying, modifying or distributing the software (or * // * any work based on the software) you agree to acknowledge its * // * use in resulting scientific publications, and indicate your * // * acceptance of all terms of the Geant4 Software license. * // ******************************************************************** // // $Id: G4DimensionedType.hh,v 1.3 2006/12/13 15:44:09 gunter Exp $ // GEANT4 tag $Name: geant4-09-04-beta-01 $ // // Generic dimensioned type. // // Jane Tinslay, September 2006 // #ifndef G4DIMENSIONEDTYPE_HH #define G4DIMENSIONEDTYPE_HH #include "globals.hh" #include "G4ConversionFatalError.hh" #include "G4String.hh" #include "G4UnitsTable.hh" #include namespace { // Helper class class HasName{ public: HasName(const G4String& name): fName(name) {}; bool operator()(const G4UnitDefinition* value) const { return ((value->GetName() == fName) || (value->GetSymbol() == fName)); } private: G4String fName; }; // Get unit value from input string. Return value indicates if // conversion was successful. G4bool GetUnitValue(const G4String& unit, G4double& value) { // Get units table G4UnitsTable& unitTable = G4UnitDefinition::GetUnitsTable(); if (unitTable.size() == 0) G4UnitDefinition::BuildUnitsTable(); // Iterate over unit lists, searching for unit match G4UnitsTable::const_iterator iterTable = unitTable.begin(); HasName myUnit(unit); G4bool gotUnit(false); while (!gotUnit && (iterTable != unitTable.end())) { G4UnitsContainer unitContainer = (*iterTable)->GetUnitsList(); G4UnitsContainer::const_iterator iterUnits = std::find_if(unitContainer.begin(), unitContainer.end(), myUnit); if (iterUnits != unitContainer.end()) { value = (*iterUnits)->GetValue(); gotUnit = true; } iterTable++; } return gotUnit; } } // Default error handling done through G4ConversionFatalError template class G4DimensionedType : public ConversionErrorPolicy { public: // Constructors G4DimensionedType(); G4DimensionedType(const T& value, const G4String& unit); // Destructor virtual ~G4DimensionedType(); // Accessors // Raw, undimensioned value T RawValue() const; // Unit string G4String Unit() const; // Dimensioned value - rawValue*converted unit T DimensionedValue() const; // Operators T operator()() const; bool operator == (const G4DimensionedType& rhs) const; bool operator != (const G4DimensionedType& rhs) const; bool operator < (const G4DimensionedType& rhs) const; bool operator > (const G4DimensionedType& rhs) const; private: // Data members T fValue; G4String fUnit; T fDimensionedValue; }; template G4DimensionedType::G4DimensionedType() :fValue(0) ,fUnit("Undefined") ,fDimensionedValue(0) {} template G4DimensionedType::G4DimensionedType(const T& value, const G4String& unit) :fValue(value) ,fUnit(unit) { G4double unitValue(0); // Convert unit string to unit value if (!GetUnitValue(unit, unitValue)) ConversionErrorPolicy::ReportError(unit, "Invalid unit"); fDimensionedValue = value*unitValue; } template G4DimensionedType::~G4DimensionedType() {} template T G4DimensionedType::RawValue() const { return fValue; } template G4String G4DimensionedType::Unit() const { return fUnit; } template T G4DimensionedType::DimensionedValue() const { return fDimensionedValue; } template T G4DimensionedType::operator()() const { return fDimensionedValue; } template bool G4DimensionedType::operator == (const G4DimensionedType& rhs) const { return fDimensionedValue == rhs.fDimensionedValue; } template bool G4DimensionedType::operator != (const G4DimensionedType& rhs) const { return fDimensionedValue != rhs.fDimensionedValue; } template bool G4DimensionedType::operator < (const G4DimensionedType& rhs) const { return fDimensionedValue < rhs.fDimensionedValue; } template bool G4DimensionedType::operator > (const G4DimensionedType& rhs) const { return fDimensionedValue > rhs.fDimensionedValue; } template std::ostream& operator << (std::ostream& os, const G4DimensionedType& obj) { os << obj.RawValue()<<" "<