Salve a tutti,
volevo chiedere se qualcuno fosse in grado di scrivere una funzione in linguaggio C che permetta di ottenere la trasposta di una matrice di NxM elementi interi.
Il metodo richiesto è quello ricorsivo, che a me personalmente da parecchi problemi.
Vi ringrazio in anticipo per le risposte che manderete. Ciao a tutti.

chiesto 24 Lug '13, 18:14

luca's gravatar image

luca
35114

modificato 20 Ago '13, 13:18

enzotib's gravatar image

enzotib ♦♦
14.0k112186

Ciao, ok, grazie mille, ora ci provo!

(25 Lug '13, 19:29) luca luca's gravatar image

Ecco una soluzione completa di stampa dei risultati.

La trasposta viene calcolata per ogni matrice N,M in maniera puramente ricorsiva. La funzione è lineare.

#include <stdio.h>
#define N 2
#define M 3
/*
Stampa una matrice di dimensioni n,m
*/
void print(void *A, const int n, const int m){
    int i,j;
    int *mat=(int*)A;
    printf("%ix%i matrix:\n",n,m);
    for(i=0; i<n; i++){
        printf("|");
        for(j=0; j<m; j++){
            printf("\t%i",mat[i*m+j]);
        }
        printf("\t|\n");
    }
}
/*
Calcola At, la trasposta della matrice A
Il parametro k deve essere inizialmente 0
Il risultato viene salvato in At che deve essere già stata allocata
*/
void traspose(int A[N][M], int At[M][N], int k){
    if(k<N*M){
        int i=k%M;
        int j=k/M;
        At[i][j]=A[j][i];
        traspose(A,At,k+1);
    }
}
int main(int argc, char* argv[]){
    int A[N][M] = {{1, 2, 3}, {4, 5, 6}};//2x3
    int At[M][N];//3x2

    traspose(A,At,0);

    print(A,N,M);
    print(At,M,N);

    return 0;
}
coll. permanente

ha risposto 25 Lug '13, 15:30

Marco's gravatar image

Marco
1.5k4930

modificato 25 Lug '13, 16:05

A scuola mi han fatto scrivere questo, ma AFAIK le trasposte si fanno solo con matrici quadrate (la dimensione è impostata dalla costante N) (non stampa niente, se vuoi stampare aggiungi le righe)

#include<stdlib.h>
#define N 4

int main(){
    int A[N][N], T[N][N], i, j;
    srand((unsigned) time(NULL));
    for(i=0; i<N; i++)
        for(j=0; j<N; j++)
            A[i][j] = rand()%50+1;
    for(i=0; i<N; i++)
        for(j=0; j<N; j++)
            T[i][j] = A[j][i];
    return 0;
}

Se qualcuno vuole migliorarlo, è il benvenuto!

coll. permanente
Questa risposta è segnata come "wiki".

ha risposto 24 Lug '13, 22:46

mapreri's gravatar image

mapreri
759617

Ciao,prima di tutto grazie della risposta, poi, a me sarebbe servito un metodo ricorsivo e la trasposta avrei dovuto calcolarla all'interno di una funzione. Inoltre non era specificatamente indicato che la matrice dovesse essere quadrata, ma naturalmente le dimensioni, almeno per quanto riguarda nel mio testo dovevano essere prefissate con delle define. Il fatto è che a me servirebbe un metodo ricorsivo,che non riesco ad identificare!

(25 Lug '13, 08:01) luca luca's gravatar image

La trasposta esiste per qualsiasi matrice. Se parti da una matrice nxm semplicemente ne ottieni una mxn.

Per fare la ricorsione, comunque, innanzitutto devi individuare uno (o più) parametri da far variare, alcuni invarianti che sono verificati dai tuoi dati di input/output ma, soprattutto, una condizione di stop che ti chiude la ricorsione.

Poi devi scrivere una funzione che abbia come input la stessa cosa che dà come output.

Cosa dovrà dare in input/output la tua funzione ricorsiva? Ovviamente una matrice. Che in input è da trasporre e in output è la trasposta di quella di partenza.

Qual è la condizione di stop? Che la matrice abbia una riga sola (e ritorni la trasposta di questa riga).

Dopo di che, direi che uno pseudo codice per l'algoritmo potrebbe essere più o meno questo:

trasponiVec(vettore) {
  IN: vettore riga
  OUT: vettore colonna trasposto di quello di prima

FOR i = 0 .. #vettore - 1 DO 
  nuovo_vettore[i, 0] = vettore[0, i]

RETURN nuovo_vettore
}

trasponiRec(Matrice) {
  IN: matrice da trasporre
  OUT: matrice trasposta

IF #righe = 1 THEN
  RETURN trasponiVec(questa riga)
ELSE
  RETURN (trasponiRec(Matrice meno ultima riga) APPEND trasponiVec(ultima riga)); 
}
coll. permanente

ha risposto 25 Lug '13, 10:43

dadexix86's gravatar image

dadexix86 ♦♦
16.9k816161

modificato 25 Lug '13, 14:33

Comunque sì, il C supporta la ricorsione.

(25 Lug '13, 13:52) enzotib ♦♦ enzotib's gravatar image

Ok, grazie :) A me avevano fatto fare la ricorsione durante il corso di C++, non durante quello di C, quindi non credevo lo facesse, modifico la mia risposta :)

(25 Lug '13, 14:33) dadexix86 ♦♦ dadexix86's gravatar image
La tua risposta
abilita/disabilita anteprima

Segui questa domanda

Via email:

Una volta eseguito l'accesso potrai iscriverti a tutti gli aggiornamenti qui

Via RSS:

Risposte

Risposte e commenti

Basi di markdown

  • *corsivo* o __corsivo__
  • **grassetto** o __grassetto__
  • collegamento:[testo](http://url.com/ "titolo")
  • immagine?![alt testo](/path/img.jpg "titolo")
  • elenco numerato: 1. Foo 2. Bar
  • per aggiungere un'interruzione di riga, aggiungi due spazi a fine riga e premi «Invio»
  • è supportato anche semplice HTML

Tag:

×103
×22

domanda posta: 24 Lug '13, 18:14

domanda visualizzata: 2,296 volte

ultimo aggiornamento: 20 Ago '13, 13:18

Chiedi è un servizio di supporto gestito da Ubuntu-it. Contattaci!

powered by OSQAPostgreSQL database
Ubuntu e Canonical sono marchi registrati da Canonical Ltd.