infoarena

infoarena - concursuri, probleme, evaluator, articole => Informatica => Subiect creat de: Dragos din Ianuarie 21, 2010, 18:38:37



Titlul: return matrice
Scris de: Dragos din Ianuarie 21, 2010, 18:38:37
cum se mai returneaza o matrice si functia de ce tip trebuie sa fie?
Cod:
#include<iostream>
using namespace std;
int[3][3] gigi(int a[3][3])
{
    return a;
}
int main()
{int i,j,a[3][3]={{1,2,3},{1,2,3},{1,2,3}};
for(i=0;i<=2;i++)
  {for(j=0;j<=2;j++)
  a=gigi(a);
   cout<<a[i][j]<<" ";
   cout<<'\n';

  }
  return 0;
}
[code\]


Titlul: Răspuns: return matrice
Scris de: Savin Tiberiu din Ianuarie 21, 2010, 19:06:19
Cod:
int** gigi(int** a) {
  return a;
}

Ar trebui sa mai mearga si in felul asta dar nu sunt sigur:
Cod:
int[][3] gigi(int[][3] a) {
  return a;
}


Titlul: Răspuns: return matrice
Scris de: Dragos din Ianuarie 21, 2010, 19:07:47
Cod:
int** gigi(int** a) {
  return a;
}

Ar trebui sa mai mearga si in felul asta dar nu sunt sigur:
Cod:
int[][3] gigi(int[][3] a) {
  return a;
}



nu nu merge nici nu trtece de faza de compilare:
zice gigi was not declared in this scope


Titlul: Răspuns: return matrice
Scris de: Mircea Dima din Ianuarie 21, 2010, 19:38:17
incearca cu stl

Cod:
#include <cstdio>
#include <vector>

using namespace std;

typedef vector<vector<int> > vvi;

vvi a;

vvi f(vvi a)
{
a[1][2] = 1;
return a;
}

int main()
{
a.resize(10);
for(int i = 0; i < 10; ++i)
a[i].resize(10);

a = f(a);

printf("%d\n", a[1][2]);
return 0;
}



Titlul: Răspuns: return matrice
Scris de: Dragos din Ianuarie 21, 2010, 19:44:51
deci merge cu codul asta la mine pe winDOS dar la recomandarea cuiva care zicea ca nu e bine si ca nu va merge intotdeana am creat un subiect nou pe care va rog sa-l cititi si sa-mi spuneti cum se comporta codul pe linux
Cod:
#include<iostream>
using namespace std;

int gigi(int a[3][3])
{ a[1][1]=7;
  return **a;
}
int main()
{int i,j,a[3][3]={{1,2,3},{1,2,3},{1,2,3}};
**a=gigi(a);
for(i=0;i<=2;i++)
  {for(j=0;j<=2;j++)

   cout<<a[i][j]<<" ";
   cout<<'\n';

  }
  return 0;
}


Titlul: Răspuns: return matrice
Scris de: alexandru din Ianuarie 21, 2010, 22:03:44
Ce vrei tu nu se poate. Matricea nu este un tip de data. int** a nu este o matrice!!
Varianta
Cod:
#include <iostream>
#include <cstdlib>

/*
 *
 */
using namespace std;
int** gigi( int** a )
{
    return a;
}
void output( int ** a )
{
    for( int i=0; i < 3; ++i )
    {
        for( int j=0; j < 3; ++j )
            cout<<a[i][j]<<' ';
        cout<<'\n';
    }
    cout<<'\n';
}
int main()
{
    int **a, **b;
    int i, j;
    a=(int**)malloc( 3*sizeof(int) );
    for( i=0; i < 3; ++i )
    {
        a[i]=(int*)calloc( 3, sizeof(int) );
        for( j=1; j < 3; ++j )
            a[i][j]=a[i][j-1]+1;
    }
    b=gigi(a);
    output( a );
    output( b );
    b[0][0]=10;
    output( a );
    output( b );
    return 0;
}
doar atribuie adresa lui a la adresa lui b. Practic daca faci vreo schimbare in a  se face si in b si invers.


Titlul: Răspuns: return matrice
Scris de: Andrei Grigorean din Ianuarie 21, 2010, 23:52:05
Ai doua solutii:

1) Inveti pointeri si folosesti int**.
2) Inveti OOP si iti faci o clasa.


Titlul: Răspuns: return matrice
Scris de: Dragos din Ianuarie 21, 2010, 23:56:04
Ai doua solutii:

1) Inveti pointeri si folosesti int**.
2) Inveti OOP si iti faci o clasa.
2)stiu, dar nu vreau sa fac cu clasa
1) sper ca nu te referi sa scriu int** in programul de mai sus ca nu merge, crede-ma nu am stat numai eu astazi la el am incercat o groaza de variante si nu a mers(bine variante de a pune pointerii si chestii dastea ca cu <vector> merge dar nu vreau cu vector vreau cat mai simplu( cum zice semnatura lui marius :p )
in C merge programul de mai sus cu cateva modificari anume sa mai declar un pointer (**k sa zicem) in functia gigi() care sa preia informatiile di n matrice si sa returnez pointeul nu matricea dar merge doar in C am incercat in C++ pe codeblocks cu compilator de gcc si nu a mers

 


Titlul: Răspuns: return matrice
Scris de: Savin Tiberiu din Ianuarie 22, 2010, 01:28:04
Cod:
void init(int a[][3]) {
    a[0][0] = 1;
    a[1][1] = 2;
    a[2][2] = 3;
}

int main() {
    int a[3][3];
    init(a);
    for (int i = 0; i < 3; i++, printf("\n")) {
        for (int j = 0; j < 3; j++) {
            printf("%d ", a[i][j]);
        }
    }
    return 0;
}
Ideea e ca atunci cand trimiti un vector multidimensional ca matrice in felul acesta (cu []) trebuie sa ii dai toate dimensiunile in prototipul functiei mai putin la prima. Nu ai nevoie sa o returnezi pentru ca trimiterea se face prin referinta si se va actualiza.
Daca ai vrea sa zicem sa faci ceva de genul
Cod:
int[][3] blabla(param1, param2) {
   ....
   return matrice;
}

int main() {
   int mat[3][3];
   mat = blabla(param1, param2);
}
Nu o sa poti (nu stiu exact de ce dar nu prea vrea sa accepte declararea functiei, acel int[][3]). Insa poti sa faci asa:
Cod:
void blabla(param1, param2, int ret[][3]) {
   ...
}

int main() {
   int mat[3][3];
   blabla(param1, param2, mat);
}


Titlul: Răspuns: return matrice
Scris de: Andrei Grigorean din Ianuarie 22, 2010, 01:42:11
Dupa cum spuneam mai sus, poti folosi int**:

Cod:
#include<iostream>
using namespace std;

int** gigi(int** a) {
  return a;
}


int main() {
  int i, j;
  int** a;

  a = new int*[3];
  for (i = 0; i < 3; ++i)
    a[i] = new int[3];

  for (int i = 0; i < 3; ++i)
    for (int j = 0; j < 3; ++j)
      a[i][j] = j;

  for(i = 0; i <= 2; i++) {
     for(j = 0; j <= 2; j++) {
       a = gigi(a);
       cout << a[i][j] << " ";
      }
    cout << "\n";
  }

   return 0;
}

Si chiar as invata mai multe despre pointeri in locul tau ;)


Titlul: Răspuns: return matrice
Scris de: Dragos din Ianuarie 22, 2010, 08:16:47
Dupa cum spunea mai sus, poti folosi int**:

Cod:
#include<iostream>
using namespace std;

int** gigi(int** a) {
  return a;
}


int main() {
  int i, j;
  int** a;

  a = new int*[3];
  for (i = 0; i < 3; ++i)
    a[i] = new int[3];

  for (int i = 0; i < 3; ++i)
    for (int j = 0; j < 3; ++j)
      a[i][j] = j;

  for(i = 0; i <= 2; i++) {
     for(j = 0; j <= 2; j++) {
       a = gigi(a);
       cout << a[i][j] << " ";
      }
    cout << "\n";
  }

   return 0;
}

Si chiar as invata mai multe despre pointeri in locul tau ;)
pai da daca tot "te iei de mine" macar da-mi si codul  :ok:
mersi :peacefingers:


Titlul: Răspuns: return matrice
Scris de: Mircea Dima din Ianuarie 22, 2010, 09:56:28
cred ca asta e singura metoda care sa iti returneze "o noua matrice" deorece nu folosesti obiecte

Cod:
#include<iostream>
using namespace std;

int** gigi(int** a) {
    int **b = new int*[3];
    for(int i = 0; i < 3; ++i)
b[i] = new int[3];

    for(int i = 0; i < 3; ++i)
for(int j = 0; j < 3; ++j)
    b[i][j] = a[i][j];

    b[1][1] = 5;
    b[1][2] = 6;
    b[2][2] = 9;
   
  return b;
}


int main() {
  int i, j;
  int** a;

  a = new int*[3];
  for (i = 0; i < 3; ++i)
    a[i] = new int[3];

  for (int i = 0; i < 3; ++i)
    for (int j = 0; j < 3; ++j)
      a[i][j] = j;

  for(i = 0; i <= 2; i++) {
     for(j = 0; j <= 2; j++) {
       int ** x = gigi(a);
       cout << x[i][j] << " ";
      }
    cout << "\n";
  }

   return 0;
}


Titlul: Răspuns: return matrice
Scris de: Andrei Grigorean din Ianuarie 22, 2010, 11:28:28
Blasterz, ai grija la memory leaks.


Titlul: Răspuns: return matrice
Scris de: Mircea Dima din Ianuarie 22, 2010, 11:41:49
stiu... dar i-am aratat ca merge...

Cod:
#include<iostream>
using namespace std;

int** gigi(int** a) {
    int **b = new int*[3];
    for(int i = 0; i < 3; ++i)
b[i] = new int[3];

    for(int i = 0; i < 3; ++i)
for(int j = 0; j < 3; ++j)
    b[i][j] = a[i][j];

    b[1][1] = 5;
    b[1][2] = 6;
    b[2][2] = 9;
   
  return b;
}

void del(int **&x)
{
   for(int i = 0; i < 3; ++i)
       delete[] x[i];

   delete[] x;

   x = NULL;
}

int main() {
  int i, j;
  int** a;

  a = new int*[3];
  for (i = 0; i < 3; ++i)
    a[i] = new int[3];

  for (int i = 0; i < 3; ++i)
    for (int j = 0; j < 3; ++j)
      a[i][j] = j;

  for(i = 0; i <= 2; i++) {
     for(j = 0; j <= 2; j++) {
       int ** x = gigi(a);
       cout << x[i][j] << " ";
   
       del(x);
             
      }
    cout << "\n";
  }

   return 0;
}


Titlul: Răspuns: return matrice
Scris de: Dragos din Ianuarie 22, 2010, 14:17:08
Cod:
int** gigi(int** a) {
    int (*b)[3]=new int[3][3];
    for(int i = 0; i < 3; ++i)
for(int j = 0; j < 3; ++j)
   b[i][j] = a[i][j];

    b[1][1] = 5;
    b[1][2] = 6;
    b[2][2] = 9;

  return b;
}
deci ceva ca mai sus nu merge pentru ca e tablou si nu pointer **b?
si inca o intrebare de ce trebuie mereu folosit delete? se ia 100 si fara delete. tot nu8 inteleg de ce sa folosim deleta daca avem loc in memoria ram pentru toate datele pe care le folosim? daca era sa folosim o matrice sau un vector foarte mare X si sa-i punem valorile in altul Y si de X sa nu mai avem nevoie intelegeam de ce sa facem delete dar asa nu-mi dau seama
o explicatie?


Titlul: Răspuns: return matrice
Scris de: Savin Tiberiu din Ianuarie 22, 2010, 14:27:20
@blasterz: Esti sigur ca e ok sa returnezi adresa unei variabile declarate local? Stiu ca merge ca am folosit si eu odata dar gcc-u imi dadea warning si mie se parea destul de intemeiat ce zicea el acolo.


Titlul: Răspuns: return matrice
Scris de: Andrei Grigorean din Ianuarie 22, 2010, 14:58:12
@apocalypto: http://www.lysator.liu.se/c/c-faq/c-2.html. Intr-adevar, la olimpiada merge si fara sa stergi datele alocate dinamic. Insa in viata reala, oriunde ai scrie cod, trebuie sa ai grija sa stergi tot ce aloci, altfel ajungi sa ai memory leaks (http://en.wikipedia.org/wiki/Memory_leak).

@devilkind: El nu returneaza adresa unei variabile declarate local, ci valoarea ei.


Titlul: Răspuns: return matrice
Scris de: Dragos din Ianuarie 22, 2010, 15:24:29
@apocalypto: http://www.lysator.liu.se/c/c-faq/c-2.html. Intr-adevar, la olimpiada merge si fara sa stergi datele alocate dinamic. Insa in viata reala, oriunde ai scrie cod, trebuie sa ai grija sa stergi tot ce aloci, altfel ajungi sa ai memory leaks (http://en.wikipedia.org/wiki/Memory_leak).

@devilkind: El nu returneaza adresa unei variabile declarate local, ci valoarea ei.
corect
mersi pentru linkuri