50 #ifndef _ZOLTAN2_INTEGERRANGELIST_HPP_ 51 #define _ZOLTAN2_INTEGERRANGELIST_HPP_ 53 #include <Zoltan2_config.h> 55 #include <Teuchos_ParameterEntryValidator.hpp> 56 #include <Teuchos_ValidatorXMLConverter.hpp> 57 #include <Teuchos_XMLObject.hpp> 58 #include <Teuchos_ValidatorMaps.hpp> 59 #include <Teuchos_DummyObjectGetter.hpp> 60 #include <Teuchos_StrUtils.hpp> 95 template <
typename Integral>
98 typedef typename Teuchos::Array<Integral>::size_type arraySize_t;
99 arraySize_t len = vals.size();
103 Integral flag = vals[len-1];
125 template <
typename Integral>
129 throw std::runtime_error(
"list is not a valid range list");
147 template <
typename Integral>
150 if (!e.isType<Teuchos::Array<Integral> >())
151 throw std::runtime_error(
"Should not call until modified");
153 Teuchos::Array<Integral> *valPtr=NULL;
154 Teuchos::Array<Integral> &
vals = e.getValue(valPtr);
172 template <
typename Integral>
176 throw std::runtime_error(
"list is not a valid range list");
194 template <
typename Integral>
197 if (!e.isType<Teuchos::Array<Integral> >())
198 throw std::runtime_error(
"Should not call until modified");
200 Teuchos::Array<Integral> *valPtr=NULL;
201 Teuchos::Array<Integral> &
vals = e.getValue(valPtr);
219 template <
typename Integral>
220 bool IsInRangeList(
const Integral val,
const Teuchos::Array<Integral> &valList,
bool sorted=
true)
228 typename Teuchos::Array<Integral>::const_iterator flag = valList.end();
230 if (std::binary_search(valList.begin(), flag, val))
236 for (
typename Teuchos::Array<Integral>::size_type i=0; i < valList.size()-1; i++){
237 if (valList[i] == val)
254 template <
typename Integral>
257 if (!e.isType<Teuchos::Array<Integral> >())
258 throw std::runtime_error(
"Should not call until modified");
260 Teuchos::Array<Integral> *valPtr=NULL;
261 Teuchos::Array<Integral> &valList = e.getValue(valPtr);
264 RCP<const irl_t> irl;
267 RCP<const Teuchos::ParameterEntryValidator> valtor = e.validator();
268 if (!valtor.is_null()){
270 irl = rcp_dynamic_cast<
const irl_t>(valtor);
281 throw std::runtime_error(
"wrong type of parameter entry");
283 bool sorted = irl->inputListWillBeSorted();
296 template <
typename Integral>
297 Teuchos::ArrayView<Integral>
getList(Teuchos::Array<Integral> &irl)
299 Teuchos::ArrayView<Integral> av;
303 av = irl.view(0, irl.size()-1);
316 template <
typename Integral>
324 Teuchos::ArrayView<const Integral> view =
325 irl.view(0, irl.size()-1);
393 template <
typename Integral>
398 #ifndef DOXYGEN_SHOULD_SKIP_THIS 404 static const std::string listDelim_;
405 static const std::string rangeDelim_;
406 static const std::string allText_;
408 static void checkValid(
char c);
409 static bool listSaysAll(std::string &l);
410 static int breakRange(std::string &range, std::string &from, std::string &to);
432 bool unsorted=
false);
438 void printDoc(std::string
const& docString, std::ostream &out)
const;
442 void validate( Teuchos::ParameterEntry
const& entry,
443 std::string
const&
paramName, std::string
const& sublistName
447 std::string
const& sublistName, Teuchos::ParameterEntry * entry
480 template <
typename Integral>
483 template <
typename Integral>
486 template <
typename Integral>
489 template <
typename Integral>
492 if (std::isspace(c) || std::isdigit(c) || (c ==
',') || (c ==
'-'))
495 throw std::runtime_error(
"invalid integer range list");
498 template <
typename Integral>
501 std::transform(l.begin(), l.end(), l.begin(), (int(*)(int)) tolower);
502 if (l.find(allText_) != std::string::npos)
508 template <
typename Integral>
510 std::string &range, std::string &from, std::string &to)
514 std::string::size_type loc = range.find(rangeDelim_);
515 if (loc == std::string::npos){
519 from = range.substr(0, loc);
520 to = range.substr(loc+1, range.size());
523 std::istringstream iss1(from);
527 std::istringstream iss2(to);
532 return (b != a) ? 2 : 1;
536 template <
typename Integral>
538 bool unsorted): min_(1), max_(0), unsorted_(unsorted)
542 template <
typename Integral>
544 Integral validMin, Integral validMax,
bool unsorted) :
545 min_(validMin), max_(validMax), unsorted_(unsorted)
547 if (min_ < max_) std::swap(min_,max_);
552 template <
typename Integral>
556 std::string className(
"IntegerRangeListValidator");
557 std::string classType(
"("+Teuchos::TypeNameTraits<Integral>::name()+
")");
558 return std::string(className + classType);
561 template <
typename Integral>
563 std::string
const& docString, std::ostream &out)
const 565 Teuchos::StrUtils::printLines(out,
"# ",docString);
566 out <<
"#\tAn integer range list is a string which can contain:\n";
567 out <<
"#\t\tthe text \"all\", which indicates all values\n";
568 out <<
"#\t\ta list of integer ranges separated by commas.\n";
569 out <<
"#\tA range is one value, or two values separated by a dash.\n";
570 out <<
"#\tExample: \"all\" or \"1-10\" or \"3, 10-12\" or \"25\"\n";
572 out <<
"#\tThe range of valid integers is [";
573 out << min_ <<
"," << max_ <<
"]\n";
577 template <
typename Integral>
580 return Teuchos::null;
583 template <
typename Integral>
585 Teuchos::ParameterEntry
const& entry,
586 std::string
const&
paramName, std::string
const& sublistName)
const 588 if (!entry.isType<std::string>()){
591 std::string *sptr=NULL;
592 std::string &rangeList = entry.getValue(sptr);
593 std::string inValue(rangeList);
595 if (listSaysAll(inValue))
599 std::for_each(inValue.begin(), inValue.end(), checkValid);
602 std::string::const_iterator rangeBegin = inValue.begin();
603 std::string::const_iterator valueEnd = inValue.end();
605 while (rangeBegin != valueEnd){
606 std::string::const_iterator rangeEnd = std::search(
607 rangeBegin, valueEnd, listDelim_.begin(), listDelim_.end());
608 std::string range(rangeBegin, rangeEnd);
609 std::string aHalf, bHalf;
610 int count = breakRange(range, aHalf, bHalf);
613 std::istringstream iss1(aHalf);
616 std::istringstream iss2(bHalf);
622 if ((a < min_) || (b > max_)){
623 std::ostringstream oss;
624 oss <<
"input range [" << a <<
"," << b <<
"] ";
625 oss <<
"exceeds valid range [" << min_ <<
"," << max_ <<
"] ";
626 throw std::runtime_error(oss.str());
628 if (rangeEnd == valueEnd)
629 rangeBegin = rangeEnd;
631 rangeBegin = ++rangeEnd;
636 template <
typename Integral>
638 std::string
const&
paramName, std::string
const& sublistName,
639 Teuchos::ParameterEntry * entry)
const 641 typedef typename Teuchos::Array<Integral>::size_type arraySize_t;
642 if (!entry->isType<std::string>()){
646 std::string *sptr=NULL;
647 std::string &rangeList = entry->getValue(sptr);
648 Teuchos::Array<Integral> valueList;
650 std::string inValue(rangeList);
652 if (listSaysAll(inValue)){
657 std::for_each(inValue.begin(), inValue.end(), checkValid);
659 std::string::const_iterator rangeBegin = inValue.begin();
660 std::string::const_iterator valueEnd = inValue.end();
662 while (rangeBegin != valueEnd){
663 std::string::const_iterator rangeEnd = std::search(rangeBegin,
664 valueEnd, listDelim_.begin(), listDelim_.end());
665 std::string range(rangeBegin, rangeEnd);
666 std::string aHalf, bHalf;
667 int count = breakRange(range, aHalf, bHalf);
670 std::istringstream iss1(aHalf);
673 std::istringstream iss2(bHalf);
679 if ((max_ >= min_) && ((a < min_) || (b > max_))){
680 std::ostringstream oss;
681 oss <<
"input range [" << a <<
"," << b <<
"] ";
682 oss <<
"exceeds valid range [" << min_ <<
"," << max_ <<
"] ";
683 throw std::runtime_error(oss.str());
685 for (Integral i=a; i <=b; i++)
686 valueList.push_back(i);
687 if (rangeEnd == valueEnd)
688 rangeBegin = rangeEnd;
690 rangeBegin = ++rangeEnd;
692 if (!unsorted_ && valueList.size() > 1){
693 std::sort(valueList.begin(), valueList.end());
694 arraySize_t listEnd = 0;
695 arraySize_t length = valueList.size();
696 for (arraySize_t i=1; i < length; i++){
697 if (valueList[i] > valueList[listEnd]){
700 valueList[listEnd] = valueList[i];
703 if (++listEnd < length)
704 valueList.resize(listEnd);
708 if (valueList.size() == 0){
711 else if (max_ >= min_){
712 Integral allSize = max_ - min_ + 1;
713 if (valueList.size() == allSize){
718 valueList.push_back(flag);
720 entry->setValue(valueList);
739 template <
typename Integral>
745 RCP<Teuchos::ParameterEntryValidator> convertXML(
746 const Teuchos::XMLObject& xmlObj,
747 const Teuchos::IDtoValidatorMap& validatorIDsMap)
const;
749 void convertValidator(
750 const RCP<const Teuchos::ParameterEntryValidator> validator,
751 Teuchos::XMLObject& xmlObj,
752 const Teuchos::ValidatortoIDMap& validatorIDsMap)
const;
754 #ifdef HAVE_TEUCHOS_DEBUG 756 RCP<const Teuchos::ParameterEntryValidator> getDummyValidator()
const{
757 return Teuchos::DummyObjectGetter<IntegerRangeListValidator<Integral> >::getDummyObject();
762 template <
typename Integral>
763 RCP<Teuchos::ParameterEntryValidator>
765 const Teuchos::XMLObject& xmlObj,
766 const Teuchos::IDtoValidatorMap& )
const 768 Integral minValue=0, maxValue=0;
769 bool unsorted=
false, hasMin=
false, hasMax=
false;
771 if (xmlObj.hasAttribute(std::string(
"min"))) {
772 minValue = xmlObj.getRequired<Integral>(std::string(
"min"));
776 if (xmlObj.hasAttribute(std::string(
"max"))) {
777 maxValue = xmlObj.getRequired<Integral>(std::string(
"max"));
781 if (xmlObj.hasAttribute(std::string(
"unsorted")))
782 unsorted = xmlObj.getRequired<
bool>(std::string(
"unsorted"));
784 RCP<Teuchos::ParameterEntryValidator> toReturn;
786 if (hasMin && hasMax)
788 else if (!hasMin && !hasMax)
791 throw std::runtime_error(
"invalid XML representation");
796 template<
typename Integral>
798 const RCP<const Teuchos::ParameterEntryValidator > validator,
799 Teuchos::XMLObject& xmlObj,
800 const Teuchos::ValidatortoIDMap& )
const 802 RCP<const IntegerRangeListValidator<Integral> > castedValidator =
807 Integral maxValue = castedValidator->getAllowedMaximum();
808 bool unsorted = castedValidator->inputListWillBeSorted();
810 if (minValue < maxValue){
811 xmlObj.addAttribute<Integral>(std::string(
"min"), minValue);
812 xmlObj.addAttribute<Integral>(std::string(
"max"), maxValue);
815 xmlObj.addAttribute<
bool>(std::string(
"unsorted"), unsorted);
void validateAndModify(std::string const ¶mName, std::string const &sublistName, Teuchos::ParameterEntry *entry) const
the listed values are in the Array<int>
ValidStringsList validStringValues() const
XML conversion code for IntegerRangeListValidator.
RangeType
Codes that indicate how to interpret the Array<int> representing the user's integer range list...
void convertValidator(const RCP< const Teuchos::ParameterEntryValidator > validator, Teuchos::XMLObject &xmlObj, const Teuchos::ValidatortoIDMap &validatorIDsMap) const
A ParameterList validator for integer range lists.
const std::string getXMLTypeName() const
Integral getAllowedMinimum() const
Return the minimum value permitted in the list.
bool inputListWillBeSorted() const
Return whether the list is sorted or not.
Integral getAllowedMaximum() const
Return the maximum value permitted in the list.
bool validIntegralRangeList(const Teuchos::Array< Integral > &vals)
A helper function that indicates whether an array is a valid integer range list.
bool IsInRangeList(const Integral val, const Teuchos::Array< Integral > &valList, bool sorted=true)
A helper function that determines if a value is in the list.
Teuchos::RCP< const Teuchos::Array< std::string > > ValidStringsList
static const std::string fail
void validate(Teuchos::ParameterEntry const &entry, std::string const ¶mName, std::string const &sublistName) const
bool noValuesAreInRangeList(const Teuchos::Array< Integral > &vals)
A helper function that determines if no values are in the list.
IntegerRangeListValidator(bool unsorted=false)
Constructor: any Integral is valid.
void printIntegralRangeList(std::ostream &os, Teuchos::Array< Integral > &irl)
A helper function that prints the meaning of an encoded integer range list.
Teuchos::ArrayView< Integral > getList(Teuchos::Array< Integral > &irl)
A helper function that returns a view of the list.
void printDoc(std::string const &docString, std::ostream &out) const
RCP< Teuchos::ParameterEntryValidator > convertXML(const Teuchos::XMLObject &xmlObj, const Teuchos::IDtoValidatorMap &validatorIDsMap) const
bool allValuesAreInRangeList(const Teuchos::Array< Integral > &vals)
A helper function that determines if all values are in the list.