Files
opm-common/opm/parser/eclipse/Deck/DeckRecord.cpp
Jørgen Kvalsvik fdb772e075 DeckItem without internal inheritance.
Replaces the internal inheritance + unique_ptr scheme to a flat sum type
similar scheme that uses a tag to determine which operations are legal,
rather than using the indirection itself as a tag.
2016-11-07 12:24:38 +01:00

134 lines
3.7 KiB
C++

/*
Copyright 2013 Statoil ASA.
This file is part of the Open Porous Media project (OPM).
OPM is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
OPM is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with OPM. If not, see <http://www.gnu.org/licenses/>.
*/
#include <unordered_set>
#include <stdexcept>
#include <string>
#include <algorithm>
#include <opm/parser/eclipse/Deck/DeckItem.hpp>
#include <opm/parser/eclipse/Deck/DeckRecord.hpp>
namespace Opm {
DeckRecord::DeckRecord( std::vector< DeckItem >&& items ) :
m_items( std::move( items ) ) {
std::unordered_set< std::string > names;
for( const auto& item : this->m_items )
names.insert( item.name() );
if( names.size() == this->m_items.size() )
return;
names.clear();
std::string msg = "Duplicate item names in DeckRecord:";
for( const auto& item : this->m_items ) {
if( names.count( item.name() ) != 0 )
msg += std::string( " " ) += item.name();
names.insert( item.name() );
}
throw std::invalid_argument( msg );
}
size_t DeckRecord::size() const {
return m_items.size();
}
void DeckRecord::addItem( DeckItem deckItem ) {
if( this->hasItem( deckItem.name() ) )
throw std::invalid_argument(
"Item with name: "
+ deckItem.name()
+ " already exists in DeckRecord");
m_items.push_back( std::move( deckItem ) );
}
DeckItem& DeckRecord::getItem( size_t index ) {
return this->m_items.at( index );
}
DeckItem& DeckRecord::getItem(const std::string& name) {
const auto eq = [&name]( const DeckItem& e ) {
return e.name() == name;
};
auto item = std::find_if( m_items.begin(), m_items.end(), eq );
if( item == m_items.end() )
throw std::invalid_argument("Item: " + name + " does not exist.");
return *item;
}
DeckItem& DeckRecord::getDataItem() {
if (m_items.size() == 1)
return getItem(0);
else
throw std::range_error("Not a data keyword ?");
}
const DeckItem& DeckRecord::getItem( size_t index ) const {
return this->m_items.at( index );
}
const DeckItem& DeckRecord::getItem(const std::string& name) const {
const auto eq = [&name]( const DeckItem& e ) {
return e.name() == name;
};
auto item = std::find_if( this->begin(), this->end(), eq );
if( item == m_items.end() )
throw std::invalid_argument("Item: " + name + " does not exist.");
return *item;
}
const DeckItem& DeckRecord::getDataItem() const {
if (m_items.size() == 1)
return getItem(0);
else
throw std::range_error("Not a data keyword ?");
}
bool DeckRecord::hasItem(const std::string& name) const {
const auto eq = [&name]( const DeckItem& e ) {
return e.name() == name;
};
return std::any_of( this->begin(), this->end(), eq );
}
DeckRecord::const_iterator DeckRecord::begin() const {
return this->m_items.begin();
}
DeckRecord::const_iterator DeckRecord::end() const {
return this->m_items.end();
}
}