Newsgroup: it.comp.lang.c++
Titolo: allocazione matrice

Ciao a tutti...chi di voi sarebbe cosě gentile da chiarirmi questo dubbio?
So che per allocare dinamicamente un vettore, magari data una variale Size
data in ingresso dall'utente, devo fare cosě (almeno credo):
int *base=new int[Size];
e da quanto ho capito in base ho memorizzato l'indirizzo dell'elemento [0]
dell'array.
Il mio problema č: e se voglio allocare dinamicamente una array a due
dimensioni?
L'utente mi deve dare in ingresso SizeX e SizeY della matrice, e io devo
crearla..Putroppo non sono riuscito a trovare da nessuna parte come si
fa....Mi pare di avere capito, leggendo il Lippman (Corso di Programmazione
C++) che non posso farlo, cioč, una delle due dimensioni deve essere nota a
tempo di compilazione. Ho letto giusto? E allora come faccio? Vi prego
qualcuno di voi mi dia una dritta perchč č tutta sera che sono bloccato su
questo dettaglio. Grazie in anticipo e ciao a tutti.
Gianca
-----------

 Gianca
Ciao!

 devi usare un "array di array" e fare un ciclo che percorre la prima
[CUT]
hem.. nulla gli vieta di fare un unica allocazione di  dimensione = SizeX * SizeY
e poi usarla come una matrice...
qualche cosa del tipo
int *base=new int[SizeX * SizeY];
e poi usarlo tranquillamente come base[i,j]
Ciauz

"Giò" ha scritto
:
: hem.. nulla gli vieta di fare un unica allocazione di  dimensione = SizeX
* SizeY
: e poi usarla come una matrice...
:
: qualche cosa del tipo
:
: int *base=new int[SizeX * SizeY];
:
: e poi usarlo tranquillamente come base[i,j]
:
Non proprio tranquillamente, ma con un po' di fantasia ci
si riesce:
#include <iostream>
struct index
{
  index(int cols)
    : cols_(cols), row_(0) {}
  int operator , (int col) const
    { return row_*cols_ + col; }
  void operator ++ ()
    { ++row_; }
  bool operator < (int rows) const
    { return row_ < rows; }
private: int cols_, row_;
};
int main()
{
  using namespace std;
  const int cols = 4, rows = 4;
  int mat[rows*cols] = {0,1,2,3,1,2,3,4,2,3,4,5,3,4,5,6};
  for (int row = 0; row < rows; ++row) {
    for (int col=0; col < cols; ++col )
      cout << mat[row, col] << ' ';
    cout << '\n';
  }
  cout << '\n';
  for (index row(cols); row < rows; ++row) {
    for (int col=0; col < cols; ++col )
      cout << mat[row, col] << ' ';
    cout << '\n';
  }
  cin.get();
  return 0;
}
ciao
Massimo

 writes:

... a meno che sappia cosa significa un comma operator in C [++] ; nel
qual caso puo' sempre usarlo come base[i,j], ma non sara' tranquillo
per nulla :-)
-- 
Maurizio Loreti                         
http://www.pd.infn.it/~loreti/mlo.html
Dept. of Physics, Univ. of Padova, Italy          loreti at pd dot infn dot it


hem..
ops..
    V E R G O G N A
forse dovevo ricontrollare quello che scrivevo: OVVIAMENTE intendevo
scrivere: base[i][j]
comunque ribadisco la fattibilità dell'operazione che si
fa anche in C
Giò

 Giò
Diego.

> se dichiaro int* base[x*y] , [...]
volevo dire int* base = new int[x*y]
!

 (propenderei per la seconda ipotesi)
Se operi direttamente sul puntatore, non puoi applicare due volte '[]'.
Perņ puoi incapsulare l'array in una classe e definire operator[] in modo
appropriato.
Ad esempio:
 template< class T, int X, int Y >
 class fixed_vector_2d
 {
  public:	 
  typedef T block_t[ Y ];
  private:
  block_t*	data_;
  public:
  fixed_vector_2d()  { data_ =  new block_t[ X ]; }
  ~fixed_vector_2d() { delete[] data_; }
  block_t& operator[]( size_t i ) { return data_[ i ] ; }
  const block_t& operator[]( size_t i ) const { return data_[ i ]; }
  // ... qui ci vuole anche il copy-ctor e operator=
 }; 
 int main()
 {
   fixed_vector_2d< int, 10, 20 > m;
   m[9][19] = 10;	
 }
Bye,
MM

 O sono io che non ho capito niente ? (propenderei per la seconda ipotesi)
probabilmente sono io che mi spiego male..
allochi la memoria e la fai puntare ad un puntatore (OVVIO... a chi sennň?)
dopo di che puoi usare il puntatore come un array...ovviamente sta a te
fare attenzione che gli "indici" dell'array non *escano* (madň come sto scrivendo
male oggi) dalla tua allocazione--

 appropriato.
ovvio che si....
ma volevo essere + "leggero"
Giò

Incidentalmente, il problema e' trattato a fondo nelle FAQ di
comp.lang.c++ [1]; e' fortemente consigliato, per l'accesso, l'uso di
operator() --- e.g., se "mat" e' un'istanza di una matrice a 2 indici,
di usare mat(i,j).
[1] 
http://www.parashift.com/c++-faq-lite/


 con un '[]' è sicuro..l'ho fatto diverse volte
Forse non ci stiamo capendo. Se lavori con un T**, allocando un array di
T* e assegnando a ciascuno di essi il puntatore a un array di T, puoi
ovviamente usare due volte []. Imho Aka Tonino, però, stava perlando di
usare un singolo array di dimensioni pari al prodotto delle colonne per le
righe. 
Max

 scrivere: base[i][j]
... che ovviamente e` sbagliato :-))
ciao Anto
-- 
"Computer science is not about computers any more than astronomy
is about telescopes." -- EW Dijkstra

Incidentalmente, il problema e' trattato a fondo nelle FAQ di
comp.lang.c++ [1]; e' fortemente consigliato, per l'accesso, l'uso di
operator() --- e.g., se definisci una classe "matrice a 2 indici", di
cui X e' una istanza, usare X(i,j).
[1] 
http://www.parashift.com/c++-faq-lite/


 Max

 male oggi) dalla tua allocazione--
Certo, cosě funziona: ma tu avevi detto nel primo post che, anche usando
questa tecnica (di allocare in una sola dimensione X*Y elementi), si poteva
accedere ad un singolo elemento applicando due volte l'operatore [] (es.:
array[3][4]) ... e ciň non č possibile!
Ciao,Diego