// // $Source: /cvsroot/gambit/gambit/sources/libgambit/pvector.imp,v $ // $Date: 2006/07/20 16:23:14 $ // $Revision: 1.3 $ // // DESCRIPTION: // Implementation of partitioned vector members // // This file is part of Gambit // Copyright (c) 2002, The Gambit Project // // This program 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 2 of the License, or // (at your option) any later version. // // This program 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 this program; if not, write to the Free Software // Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. // #include "pvector.h" namespace Gambit { //------------------------------------------------------------------------- // PVector: Private and protected member functions //------------------------------------------------------------------------- template int PVector::sum(const Array &V) const { int total = 0; for (int i = V.First(); i <= V.Last(); total += V[i++]); return total; } template void PVector::setindex(void) { int index = this->First(); for(int i = 1; i <= svlen.Length(); i++) { svptr[i] = this->data + index - 1; index += svlen[i]; } //assert(index == this->Last() + 1); } template int PVector::Check(const PVector &v) const { if (v.mindex == this->mindex && v.maxdex == this->maxdex) { for (int i = 1; i <= svlen.Length(); i++) if (svlen[i] != v.svlen[i]) return 0; return 1; } return 0; } //------------------------------------------------------------------------- // PVector: Constructors, destructor, and constructive operators //------------------------------------------------------------------------- template PVector::PVector(void) : svptr(0) { } template PVector::PVector(const Array &sig) : Vector(sum(sig)), svlen(sig) { svptr = new T *[sig.Last() - sig.First() + 1]; svptr -= 1; // align things correctly setindex(); } template PVector::PVector(const Vector &val, const Array &sig) : Vector(val), svlen(sig) { //assert(sum(svlen) == val.Length()); svptr = new T *[sig.Last() - sig.First() + 1]; svptr -= 1; setindex(); } template PVector::PVector(const PVector &v) : Vector(v), svlen(v.svlen) { svptr = new T *[v.svlen.Last() - v.svlen.First() + 1]; svptr -= 1; setindex(); } template PVector::~PVector() { if (svptr) delete [] (svptr + 1); } template PVector& PVector::operator=(const PVector &v) { if (!Check(v)) { throw DimensionException(); } Vector::operator=(v); return (*this); } template PVector& PVector::operator=(const Vector &v) { Vector::operator=(v); return (*this); } template PVector& PVector::operator=(T c) { Vector::operator=(c); return (*this); } //------------------------------------------------------------------------- // PVector: Operator definitions //------------------------------------------------------------------------- template T& PVector::operator()(int a, int b) { if (svlen.First() > a || a > svlen.Last()) { throw IndexException(); } if (1 > b || b > svlen[a]) { throw IndexException(); } return svptr[a][b]; } template const T& PVector::operator()(int a, int b) const { if (svlen.First() > a || a > svlen.Last()) { throw IndexException(); } if (1 > b || b > svlen[a]) { throw IndexException(); } return svptr[a][b]; } template PVector PVector::operator+(const PVector &v) const { if (!Check(v)) { throw DimensionException(); } PVector tmp(*this); tmp.Vector::operator+=(v); return tmp; } template PVector& PVector::operator+=(const PVector &v) { if (!Check(v)) { throw DimensionException(); } Vector::operator+=(v); return (*this); } template PVector PVector::operator-(void) const { PVector tmp(*this); for(int i=this->First(); i<=this->Last(); i++) tmp[i]= -tmp[i]; return tmp; } template PVector PVector::operator-(const PVector &v) const { if (!Check(v)) { throw DimensionException(); } PVector tmp(*this); tmp.Vector::operator-=(v); return tmp; } template PVector& PVector::operator-=(const PVector &v) { if (!Check(v)) { throw DimensionException(); } Vector::operator-=(v); return (*this); } template T PVector::operator*(const PVector &v) const { if (!Check(v)) { throw DimensionException(); } return (*this).Vector::operator*(v); } template PVector PVector::operator*(const T &c) const { PVector ret(*this); ret *= c; return ret; } template PVector& PVector::operator*=(const T c) { Vector::operator*=(c); return (*this); } template PVector PVector::operator/(T c) { PVector tmp(*this); tmp= tmp.Vector::operator/(c); return tmp; } template bool PVector::operator==(const PVector &v) const { if (!Check(v)) { throw DimensionException(); } return (*this).Vector::operator==(v); } template bool PVector::operator!=(const PVector &v) const { return !((*this)==v); } //------------------------------------------------------------------------- // PVector: General data access //------------------------------------------------------------------------- template Vector PVector::GetRow(int row) const { if (svlen.First() > row || row > svlen.Last()) { throw IndexException(); } Vector v(1, svlen[row]); for(int i=v.First(); i<=v.Last(); i++) v[i]= (*this)(row,i); return v; } template void PVector::GetRow(int row, Vector &v) const { if (svlen.First() > row || row > svlen.Last()) { throw IndexException(); } if (v.First() != 1 || v.Last() != svlen[row]) { throw DimensionException(); } for(int i=v.First(); i<=v.Last(); i++) v[i]= (*this)(row,i); } template void PVector::SetRow(int row, const Vector &v) { if (svlen.First() > row || row > svlen.Last()) { throw IndexException(); } if (v.First() != 1 || v.Last() != svlen[row]) { throw DimensionException(); } for(int i=v.First(); i<=v.Last(); i++) (*this)(row,i)= v[i]; } template void PVector::CopyRow(int row, const PVector &v) { if (!Check(v)) { throw DimensionException(); } if (svlen.First() > row || row > svlen.Last()) { throw IndexException(); } for (int i = 1; i <= svlen[row]; i++) svptr[row][i] = v.svptr[row][i]; } template const Array &PVector::Lengths(void) const { return svlen; } } // end namespace Gambit