From: Martin Kronbichler Date: Thu, 4 Sep 2014 13:06:33 +0000 (+0200) Subject: Improve assertion for access to nonlocal elements X-Git-Tag: v8.2.0-rc1~159^2 X-Git-Url: https://gitweb.dealii.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=refs%2Fpull%2F135%2Fhead;p=dealii.git Improve assertion for access to nonlocal elements --- diff --git a/include/deal.II/lac/trilinos_vector_base.h b/include/deal.II/lac/trilinos_vector_base.h index 267254275b..62bd2fda3a 100644 --- a/include/deal.II/lac/trilinos_vector_base.h +++ b/include/deal.II/lac/trilinos_vector_base.h @@ -1,7 +1,7 @@ // --------------------------------------------------------------------- // $Id$ // -// Copyright (C) 2008 - 2013 by the deal.II authors +// Copyright (C) 2008 - 2014 by the deal.II authors // // This file is part of the deal.II library. // @@ -159,20 +159,6 @@ namespace TrilinosWrappers << "An error with error number " << arg1 << " occurred while calling a Trilinos function"); - /** - * Exception - */ - DeclException3 (ExcAccessToNonLocalElement, - size_type, size_type, size_type, - << "You tried to access element " << arg1 - << " of a distributed vector, but this element is not stored " - << "on the current processor. Note: The elements stored " - << "on the current processor are within the range " - << arg2 << " through " << arg3 - << " but Trilinos vectors need not store contiguous " - << "ranges on each processor, and not every element in " - << "this range may in fact be stored locally."); - private: /** * Point to the vector we are referencing. @@ -504,13 +490,24 @@ namespace TrilinosWrappers /** * Provide access to a given element, both read and write. + * + * When using a vector distributed with MPI, this operation only makes + * sense for elements that are actually present on the calling + * processor. Otherwise, an exception is thrown. This is different from + * the el() function below that always succeeds (but returns + * zero on non-local elements). */ reference operator () (const size_type index); /** - * Provide read-only access to an element. This is equivalent to the - * el() command. + * Provide read-only access to an element. + * + * When using a vector distributed with MPI, this operation only makes + * sense for elements that are actually present on the calling + * processor. Otherwise, an exception is thrown. This is different from + * the el() function below that always succeeds (but returns + * zero on non-local elements). */ TrilinosScalar operator () (const size_type index) const; @@ -524,8 +521,7 @@ namespace TrilinosWrappers operator [] (const size_type index); /** - * Provide read-only access to an element. This is equivalent to the - * el() command. + * Provide read-only access to an element. * * Exactly the same as operator(). */ @@ -553,8 +549,10 @@ namespace TrilinosWrappers /** * Return the value of the vector entry i. Note that this function * does only work properly when we request a data stored on the local - * processor. The function will throw an exception in case the elements - * sits on another process. + * processor. In case the elements sits on another process, this function + * returns 0 which might or might not be appropriate in a given + * situation. If you rely on consistent results, use the access functions + * () or [] that throw an assertion in case a non-local element is used. */ TrilinosScalar el (const size_type index) const; @@ -858,12 +856,17 @@ namespace TrilinosWrappers /** * Exception */ - DeclException3 (ExcAccessToNonlocalElement, - size_type, size_type, size_type, + DeclException4 (ExcAccessToNonLocalElement, + size_type, size_type, size_type, size_type, << "You tried to access element " << arg1 - << " of a distributed vector, but only entries " - << arg2 << " through " << arg3 - << " are stored locally and can be accessed."); + << " of a distributed vector, but this element is not stored " + << "on the current processor. Note: There are " + << arg2 << " elements stored " + << "on the current processor from within the range " + << arg4 << " through " << arg4 + << " but Trilinos vectors need not store contiguous " + << "ranges on each processor, and not every element in " + << "this range may in fact be stored locally."); private: diff --git a/source/lac/trilinos_vector_base.cc b/source/lac/trilinos_vector_base.cc index 9249f6ab81..307983184d 100644 --- a/source/lac/trilinos_vector_base.cc +++ b/source/lac/trilinos_vector_base.cc @@ -63,9 +63,9 @@ namespace TrilinosWrappers const TrilinosWrappers::types::int_type local_index = vector.vector->Map().LID(static_cast(index)); Assert (local_index >= 0, - ExcAccessToNonLocalElement (index, - vector.vector->Map().MinMyGID(), - vector.vector->Map().MaxMyGID())); + VectorBase::ExcAccessToNonLocalElement (index, vector.local_size(), + vector.vector->Map().MinMyGID(), + vector.vector->Map().MaxMyGID())); return (*(vector.vector))[0][local_index]; @@ -240,22 +240,13 @@ namespace TrilinosWrappers // Extract local indices in the vector. TrilinosWrappers::types::int_type trilinos_i = vector->Map().LID(static_cast(index)); - TrilinosScalar value = 0.; // If the element is not present on the current processor, we can't - // continue. Just print out 0. - - // TODO: Is this reasonable? - if (trilinos_i == -1 ) - { - return 0.; - //Assert (false, ExcAccessToNonlocalElement(index, local_range().first, - // local_range().second-1)); - } + // continue. Just print out 0 as opposed to the () method below. + if (trilinos_i == -1) + return 0.; else - value = (*vector)[0][trilinos_i]; - - return value; + return (*vector)[0][trilinos_i]; } @@ -270,10 +261,11 @@ namespace TrilinosWrappers // If the element is not present on the current processor, we can't // continue. This is the main difference to the el() function. - if (trilinos_i == -1 ) + if (trilinos_i == -1) { - Assert (false, ExcAccessToNonlocalElement(index, local_range().first, - local_range().second-1)); + Assert (false, ExcAccessToNonLocalElement(index, local_size(), + vector->Map().MinMyGID(), + vector->Map().MaxMyGID())); } else value = (*vector)[0][trilinos_i];