Matrix_TriangPacked.cxx
1 // Copyright (C) 2001-2011 Vivien Mallet
2 // Copyright (C) 2003-2011 Marc DuruflĂ©
3 //
4 // This file is part of the linear-algebra library Seldon,
5 // http://seldon.sourceforge.net/.
6 //
7 // Seldon is free software; you can redistribute it and/or modify it under the
8 // terms of the GNU Lesser General Public License as published by the Free
9 // Software Foundation; either version 2.1 of the License, or (at your option)
10 // any later version.
11 //
12 // Seldon is distributed in the hope that it will be useful, but WITHOUT ANY
13 // WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
14 // FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for
15 // more details.
16 //
17 // You should have received a copy of the GNU Lesser General Public License
18 // along with Seldon. If not, see http://www.gnu.org/licenses/.
19 
20 
21 #ifndef SELDON_FILE_MATRIX_TRIANGPACKED_CXX
22 
23 #include "Matrix_TriangPacked.hxx"
24 
25 namespace Seldon
26 {
27 
28 
30 
35  template <class T, class Prop, class Storage, class Allocator>
37  ::Matrix_TriangPacked(int i, int j): Matrix_Base<T, Allocator>(i, i)
38  {
39 
40 #ifdef SELDON_CHECK_MEMORY
41  try
42  {
43 #endif
44 
45  this->data_ = Allocator::allocate((i * long(i + 1)) / 2, this);
46 
47 #ifdef SELDON_CHECK_MEMORY
48  }
49  catch (...)
50  {
51  this->m_ = 0;
52  this->n_ = 0;
53  this->data_ = NULL;
54  return;
55  }
56  if (this->data_ == NULL)
57  {
58  this->m_ = 0;
59  this->n_ = 0;
60  return;
61  }
62 #endif
63 
64  }
65 
66 
68  template <class T, class Prop, class Storage, class Allocator>
71  Storage, Allocator>& A)
72  : Matrix_Base<T, Allocator>()
73  {
74  this->m_ = 0;
75  this->n_ = 0;
76  this->data_ = NULL;
77 
78  this->Copy(A);
79  }
80 
81 
83 
87  template <class T, class Prop, class Storage, class Allocator>
89  {
90 
91 #ifdef SELDON_CHECK_MEMORY
92  try
93  {
94 #endif
95 
96  if (this->data_ != NULL)
97  {
98  Allocator::deallocate(this->data_,
99  (this->m_ * long(this->m_ + 1)) / 2);
100  this->data_ = NULL;
101  }
102 
103 #ifdef SELDON_CHECK_MEMORY
104  }
105  catch (...)
106  {
107  this->m_ = 0;
108  this->n_ = 0;
109  this->data_ = NULL;
110  }
111 #endif
112 
113  this->m_ = 0;
114  this->n_ = 0;
115  }
116 
117 
118  /*********************
119  * MEMORY MANAGEMENT *
120  *********************/
121 
122 
124 
130  template <class T, class Prop, class Storage, class Allocator>
132  ::Reallocate(int i, int j)
133  {
134 
135  if (i != this->m_)
136  {
137  this->m_ = i;
138  this->n_ = i;
139 
140 #ifdef SELDON_CHECK_MEMORY
141  try
142  {
143 #endif
144 
145  this->data_ =
146  reinterpret_cast<pointer>(Allocator::reallocate(this->data_,
147  (i*long(i+1))/2, this) );
148 
149 #ifdef SELDON_CHECK_MEMORY
150  }
151  catch (...)
152  {
153  this->m_ = 0;
154  this->n_ = 0;
155  this->data_ = NULL;
156  throw NoMemory("Matrix_TriangPacked::Reallocate(int, int)",
157  "Unable to reallocate memory for data_.");
158  }
159  if (this->data_ == NULL)
160  {
161  this->m_ = 0;
162  this->n_ = 0;
163  throw NoMemory("Matrix_TriangPacked::Reallocate(int, int)",
164  "Unable to reallocate memory for data_.");
165  }
166 #endif
167 
168  }
169  }
170 
171 
174 
188  template <class T, class Prop, class Storage, class Allocator>
190  SetData(int i, int j,
192  ::pointer data)
193  {
194  this->Clear();
195 
196  this->m_ = i;
197  this->n_ = i;
198 
199  this->data_ = data;
200  }
201 
202 
204 
208  template <class T, class Prop, class Storage, class Allocator>
210  {
211  this->data_ = NULL;
212  this->m_ = 0;
213  this->n_ = 0;
214  }
215 
216 
217  /************************
218  * CONVENIENT FUNCTIONS *
219  ************************/
220 
221 
223 
227  template <class T, class Prop, class Storage, class Allocator>
229  {
230  Allocator::memoryset(this->data_, char(0),
231  this->GetDataSize() * sizeof(value_type));
232  }
233 
234 
236  template <class T, class Prop, class Storage, class Allocator>
238  {
239  T zero, one;
240  SetComplexZero(zero);
241  SetComplexOne(one);
242 
243  this->Fill(zero);
244 
245  bool storage_col = (Storage::GetFirst(1,0) == 0);
246  if ((Storage::UpLo() && storage_col)||(!Storage::UpLo() && !storage_col))
247  {
248  long index(-1);
249  for (int i = 0; i < min(this->m_, this->n_); i++)
250  {
251  index += i+1;
252  this->data_[index] = one;
253  }
254  }
255  else if (Storage::UpLo() && !storage_col)
256  {
257  long index(0);
258  for (int i = 0; i < min(this->m_, this->n_); i++)
259  {
260  this->data_[index] = one;
261  index += this->m_-i;
262  }
263  }
264  else if (!Storage::UpLo() && storage_col)
265  {
266  long index(0);
267  for (int i = 0; i < min(this->m_, this->n_); i++)
268  {
269  this->data_[index] = one;
270  index += this->n_-i;
271  }
272  }
273  }
274 
275 
277 
281  template <class T, class Prop, class Storage, class Allocator>
283  {
284  for (long i = 0; i < this->GetDataSize(); i++)
285  SetComplexReal(i, this->data_[i]);
286  }
287 
288 
290 
293  template <class T, class Prop, class Storage, class Allocator>
294  template <class T0>
296  {
297  T x_;
298  SetComplexReal(x, x_);
299  for (long i = 0; i < this->GetDataSize(); i++)
300  this->data_[i] = x_;
301  }
302 
303 
305 
308  template <class T, class Prop, class Storage, class Allocator>
309  template <class T0>
312  {
313  this->Fill(x);
314 
315  return *this;
316  }
317 
318 
320 
323  template <class T, class Prop, class Storage, class Allocator>
325  {
326 #ifndef SELDON_WITHOUT_REINIT_RANDOM
327  srand(time(NULL));
328 #endif
329  for (long i = 0; i < this->GetDataSize(); i++)
330  SetComplexReal(rand(), this->data_[i]);
331  }
332 
333 
335 
340  template <class T, class Prop, class Storage, class Allocator>
342  {
343  for (int i = 0; i < this->m_; i++)
344  {
345  for (int j = 0; j < this->n_; j++)
346  cout << (*this)(i, j) << "\t";
347  cout << endl;
348  }
349  }
350 
351 
353 
364  template <class T, class Prop, class Storage, class Allocator>
366  ::Print(int a, int b, int m, int n) const
367  {
368  for (int i = a; i < min(this->m_, a + m); i++)
369  {
370  for (int j = b; j < min(this->n_, b + n); j++)
371  cout << (*this)(i, j) << "\t";
372  cout << endl;
373  }
374  }
375 
376 
378 
386  template <class T, class Prop, class Storage, class Allocator>
388  {
389  Print(0, 0, l, l);
390  }
391 
392 
393  /**************************
394  * INPUT/OUTPUT FUNCTIONS *
395  **************************/
396 
397 
399 
406  template <class T, class Prop, class Storage, class Allocator>
408  ::Write(string FileName) const
409  {
410  ofstream FileStream;
411  FileStream.open(FileName.c_str(), ofstream::binary);
412 
413 #ifdef SELDON_CHECK_IO
414  // Checks if the file was opened.
415  if (!FileStream.is_open())
416  throw IOError("Matrix_TriangPacked::Write(string FileName)",
417  string("Unable to open file \"") + FileName + "\".");
418 #endif
419 
420  this->Write(FileStream);
421 
422  FileStream.close();
423  }
424 
425 
427 
434  template <class T, class Prop, class Storage, class Allocator>
436  ::Write(ostream& FileStream) const
437  {
438 
439 #ifdef SELDON_CHECK_IO
440  // Checks if the file is ready.
441  if (!FileStream.good())
442  throw IOError("Matrix_TriangPacked::Write(ofstream& FileStream)",
443  "Stream is not ready.");
444 #endif
445 
446  FileStream.write(reinterpret_cast<char*>(const_cast<int*>(&this->m_)),
447  sizeof(int));
448  FileStream.write(reinterpret_cast<char*>(const_cast<int*>(&this->n_)),
449  sizeof(int));
450 
451  FileStream.write(reinterpret_cast<char*>(this->data_),
452  this->GetDataSize() * sizeof(value_type));
453 
454 #ifdef SELDON_CHECK_IO
455  // Checks if data was written.
456  if (!FileStream.good())
457  throw IOError("Matrix_TriangPacked::Write(ofstream& FileStream)",
458  string("Output operation failed.")
459  + string(" The output file may have been removed")
460  + " or there is no space left on device.");
461 #endif
462 
463  }
464 
465 
467 
474  template <class T, class Prop, class Storage, class Allocator>
476  ::WriteText(string FileName) const
477  {
478  ofstream FileStream;
479  FileStream.precision(cout.precision());
480  FileStream.flags(cout.flags());
481  FileStream.open(FileName.c_str());
482 
483 #ifdef SELDON_CHECK_IO
484  // Checks if the file was opened.
485  if (!FileStream.is_open())
486  throw IOError("Matrix_TriangPacked::WriteText(string FileName)",
487  string("Unable to open file \"") + FileName + "\".");
488 #endif
489 
490  this->WriteText(FileStream);
491 
492  FileStream.close();
493  }
494 
495 
497 
504  template <class T, class Prop, class Storage, class Allocator>
506  ::WriteText(ostream& FileStream) const
507  {
508 
509 #ifdef SELDON_CHECK_IO
510  // Checks if the stream is ready.
511  if (!FileStream.good())
512  throw IOError("Matrix_TriangPacked::WriteText(ofstream& FileStream)",
513  "Stream is not ready.");
514 #endif
515 
516  int i, j;
517  for (i = 0; i < this->GetM(); i++)
518  {
519  for (j = 0; j < this->GetN(); j++)
520  FileStream << (*this)(i, j) << '\t';
521  FileStream << '\n';
522  }
523 
524 #ifdef SELDON_CHECK_IO
525  // Checks if data was written.
526  if (!FileStream.good())
527  throw IOError("Matrix_TriangPacked::WriteText(ofstream& FileStream)",
528  string("Output operation failed.")
529  + string(" The output file may have been removed")
530  + " or there is no space left on device.");
531 #endif
532 
533  }
534 
535 
537 
544  template <class T, class Prop, class Storage, class Allocator>
546  {
547  ifstream FileStream;
548  FileStream.open(FileName.c_str(), ifstream::binary);
549 
550 #ifdef SELDON_CHECK_IO
551  // Checks if the file was opened.
552  if (!FileStream.good())
553  throw IOError("Matrix_TriangPacked::Read(string FileName)",
554  string("Unable to open file \"") + FileName + "\".");
555 #endif
556 
557  this->Read(FileStream);
558 
559  FileStream.close();
560  }
561 
562 
564 
571  template <class T, class Prop, class Storage, class Allocator>
573  ::Read(istream& FileStream)
574  {
575 
576 #ifdef SELDON_CHECK_IO
577  // Checks if the stream is ready.
578  if (!FileStream.good())
579  throw IOError("Matrix_TriangPacked::Read(ifstream& FileStream)",
580  "Stream is not ready.");
581 #endif
582 
583  int new_m, new_n;
584  FileStream.read(reinterpret_cast<char*>(&new_m), sizeof(int));
585  FileStream.read(reinterpret_cast<char*>(&new_n), sizeof(int));
586  this->Reallocate(new_m, new_n);
587 
588  FileStream.read(reinterpret_cast<char*>(this->data_),
589  this->GetDataSize() * sizeof(value_type));
590 
591 #ifdef SELDON_CHECK_IO
592  // Checks if data was read.
593  if (!FileStream.good())
594  throw IOError("Matrix_TriangPacked::Read(ifstream& FileStream)",
595  string("Input operation failed.")
596  + string(" The input file may have been removed")
597  + " or may not contain enough data.");
598 #endif
599 
600  }
601 
602 
604 
608  template <class T, class Prop, class Storage, class Allocator>
610  {
611  ifstream FileStream;
612  FileStream.open(FileName.c_str());
613 
614 #ifdef SELDON_CHECK_IO
615  // Checks if the file was opened.
616  if (!FileStream.is_open())
617  throw IOError("Matrix_Pointers::ReadText(string FileName)",
618  string("Unable to open file \"") + FileName + "\".");
619 #endif
620 
621  this->ReadText(FileStream);
622 
623  FileStream.close();
624  }
625 
626 
628 
632  template <class T, class Prop, class Storage, class Allocator>
634  ::ReadText(istream& FileStream)
635  {
636  // clears previous matrix
637  Clear();
638 
639 #ifdef SELDON_CHECK_IO
640  // Checks if the stream is ready.
641  if (!FileStream.good())
642  throw IOError("Matrix_Pointers::ReadText(ifstream& FileStream)",
643  "Stream is not ready.");
644 #endif
645 
646  // we read first line
647  string line;
648  getline(FileStream, line);
649 
650  if (FileStream.fail())
651  {
652  // empty file ?
653  return;
654  }
655 
656  // converting first line into a vector
657  istringstream line_stream(line);
658  Vector<T> first_row;
659  first_row.ReadText(line_stream);
660 
661  // and now the other rows
662  Vector<T> other_rows;
663  other_rows.ReadText(FileStream);
664 
665  // number of rows and columns
666  int n = first_row.GetM();
667  int m = 1 + other_rows.GetM()/n;
668 
669 #ifdef SELDON_CHECK_IO
670  // Checking number of elements
671  if (other_rows.GetM() != (m-1)*n)
672  throw IOError("Matrix_Pointers::ReadText(ifstream& FileStream)",
673  "The file should contain same number of columns.");
674 #endif
675 
676  this->Reallocate(m,n);
677  // filling matrix
678  if (Storage::UpLo())
679  for (int j = 0; j < n; j++)
680  this->Val(0, j) = first_row(j);
681  else
682  this->Val(0, 0) = first_row(0);
683 
684  long nb = 0;
685  if (Storage::UpLo())
686  for (int i = 1; i < m; i++)
687  {
688  for (int j = 0; j < i; j++)
689  nb++;
690 
691  for (int j = i; j < n; j++)
692  this->Val(i, j) = other_rows(nb++);
693  }
694  else
695  for (int i = 1; i < m; i++)
696  {
697  for (int j = 0; j <= i; j++)
698  this->Val(i, j) = other_rows(nb++);
699 
700  for (int j = i+1; j < n; j++)
701  nb++;
702  }
703  }
704 
705 
706 
708  // MATRIX<COLUPTRIANGPACKED> //
710 
711 
712  /*****************
713  * OTHER METHODS *
714  *****************/
715 
716 
718 
725  template <class T, class Prop, class Allocator>
727  ::Resize(int i, int j)
728  {
729 
730  // Storing the old values of the matrix.
731  long nold = this->GetDataSize();
733  for (long k = 0; k < nold; k++)
734  xold(k) = this->data_[k];
735 
736  // Reallocation.
737  this->Reallocate(i, j);
738 
739  // Filling the matrix with its old values.
740  long nmin = min(nold, this->GetDataSize());
741  for (long k = 0; k < nmin; k++)
742  this->data_[k] = xold(k);
743  }
744 
745 
747  // MATRIX<COLLOTRIANGPACKED> //
749 
750 
751  /*****************
752  * OTHER METHODS *
753  *****************/
754 
755 
757 
764  template <class T, class Prop, class Allocator>
766  ::Resize(int i, int j)
767  {
768 
769  // Storing the old values of the matrix.
770  long nold = this->GetDataSize(), iold = this->m_;
772  for (long k = 0; k < nold; k++)
773  xold(k) = this->data_[k];
774 
775  // Reallocation.
776  this->Reallocate(i, j);
777 
778  // Filling the matrix with its old values.
779  long imin = min(iold, long(i));
780  nold = 0;
781  long n = 0;
782  for (long k = 0; k < imin; k++)
783  {
784  for (long l = k; l < imin; l++)
785  this->data_[n+l-k] = xold(nold+l-k);
786 
787  n += i - k;
788  nold += iold - k;
789  }
790  }
791 
792 
794  // MATRIX<ROWUPTRIANGPACKED> //
796 
797 
798  /*****************
799  * OTHER METHODS *
800  *****************/
801 
802 
804 
811  template <class T, class Prop, class Allocator>
813  ::Resize(int i, int j)
814  {
815 
816  // Storing the old values of the matrix.
817  long nold = this->GetDataSize(), iold = this->m_;
819  for (long k = 0; k < nold; k++)
820  xold(k) = this->data_[k];
821 
822  // Reallocation.
823  this->Reallocate(i, j);
824 
825  // Filling the matrix with its old values.
826  long imin = min(iold, long(i));
827  nold = 0;
828  long n = 0;
829  for (long k = 0; k < imin; k++)
830  {
831  for (long l = k; l < imin; l++)
832  this->data_[n+l-k] = xold(nold+l-k);
833 
834  n += i - k;
835  nold += iold - k;
836  }
837  }
838 
839 
840 
842  // MATRIX<ROWLOTRIANGPACKED> //
844 
845 
846  /*****************
847  * OTHER METHODS *
848  *****************/
849 
850 
852 
859  template <class T, class Prop, class Allocator>
861  ::Resize(int i, int j)
862  {
863 
864  // Storing the old values of the matrix.
865  long nold = this->GetDataSize();
867  for (long k = 0; k < nold; k++)
868  xold(k) = this->data_[k];
869 
870  // Reallocation.
871  this->Reallocate(i, j);
872 
873  // Filling the matrix with its old values.
874  long nmin = min(nold, this->GetDataSize());
875  for (long k = 0; k < nmin; k++)
876  this->data_[k] = xold(k);
877  }
878 
879 
880 } // namespace Seldon.
881 
882 #define SELDON_FILE_MATRIX_TRIANGPACKED_CXX
883 #endif
Seldon::Matrix_TriangPacked::SetData
void SetData(int i, int j, pointer data)
Changes the size of the matrix and sets its data array (low level method).
Definition: Matrix_TriangPacked.cxx:190
Seldon::Matrix_Base
Base class for all matrices.
Definition: Matrix_Base.hxx:143
Seldon::Matrix_TriangPacked::Zero
void Zero()
Sets all elements to zero.
Definition: Matrix_TriangPacked.cxx:228
Seldon::Matrix_TriangPacked::WriteText
void WriteText(string FileName) const
Writes the matrix in a file.
Definition: Matrix_TriangPacked.cxx:476
Seldon::Vector< T >
Seldon::Matrix_TriangPacked::operator=
Matrix_TriangPacked< T, Prop, Storage, Allocator > & operator=(const Matrix_TriangPacked< T, Prop, Storage, Allocator > &A)
Duplicates a matrix (assignment operator).
Definition: Matrix_TriangPackedInline.cxx:265
Seldon::Matrix_TriangPacked::Nullify
void Nullify()
Clears the matrix without releasing memory.
Definition: Matrix_TriangPacked.cxx:209
Seldon::Matrix_TriangPacked::Write
void Write(string FileName) const
Writes the matrix in a file.
Definition: Matrix_TriangPacked.cxx:408
Seldon::Matrix
Definition: SeldonHeader.hxx:226
Seldon::Matrix_TriangPacked::Fill
void Fill()
Fills the matrix with 0, 1, 2, ...
Definition: Matrix_TriangPacked.cxx:282
Seldon::Matrix_TriangPacked::SetIdentity
void SetIdentity()
Sets the matrix to the identity.
Definition: Matrix_TriangPacked.cxx:237
Seldon::Matrix_TriangPacked::Clear
void Clear()
Clears the matrix.
Definition: Matrix_TriangPacked.cxx:88
Seldon::Matrix_TriangPacked::FillRand
void FillRand()
Fills the matrix randomly.
Definition: Matrix_TriangPacked.cxx:324
Seldon::Matrix_TriangPacked
Triangular packed matrix class.
Definition: Matrix_TriangPacked.hxx:38
Seldon::Vector< T, VectFull, Allocator >
Full vector class.
Definition: Vector.hxx:88
Seldon::Matrix_TriangPacked::Read
void Read(string FileName)
Reads the matrix from a file.
Definition: Matrix_TriangPacked.cxx:545
Seldon::Matrix_TriangPacked::ReadText
void ReadText(string FileName)
Reads the matrix from a file.
Definition: Matrix_TriangPacked.cxx:609
Seldon::Matrix_TriangPacked::Print
void Print() const
Displays the matrix on the standard output.
Definition: Matrix_TriangPacked.cxx:341
Seldon
Seldon namespace.
Definition: Array.cxx:24
Seldon::IOError
Definition: Errors.hxx:150
Seldon::Matrix_TriangPacked::Matrix_TriangPacked
Matrix_TriangPacked()
Default constructor.
Definition: Matrix_TriangPackedInline.cxx:40
Seldon::NoMemory
Definition: Errors.hxx:90
Seldon::Matrix_TriangPacked::Reallocate
void Reallocate(int i, int j)
Reallocates memory to resize the matrix.
Definition: Matrix_TriangPacked.cxx:132
Seldon::SetComplexReal
void SetComplexReal(int n, std::complex< T > &number)
Sets a complex number to (n, 0).
Definition: CommonInline.cxx:234