Originariamente inviata da
oregon
Nel codice esistono tanti problemi "minori" (ad esempio, che senso ha controllare con feof la fine del file se sai esattamente quanti caratteri leggere? Oppure controllare if(nomefile == NULL) invece di controllare l'handle restituito dalla fopen).
Il testo del problema dice che non si conosce a priori la dimensione del file, ecco il motivo per cui uso feof.
Originariamente inviata da
oregon
Ma la questione che genera l'errore è un'altra. Alla funzione leggi_matrice devi passare un puntatore a matrix (ovvero un puntatore triplo)
matrix *m
altrimenti non potrai mai modificarlo all'interno della funzione.
Ho provato ma ottengo errori quando alloco lo spazio in memoria.
codice:
#include <stdio.h>
#include <stdlib.h>
#define MAX_C 50
#define MAX_R 50
typedef char** matrix;
int R, C;
matrix *matricevip;
void leggi_matrice(const char* nomefile, matrix *m, int *r, int *c);
void stampa_matrice(matrix *m, int r, int c);
int main(int argc, char *argv[])
{
char* nomefile = argv[1];
if(argc!=2)
{
printf("Numero di argomenti inseriti errato!\n");
exit(EXIT_FAILURE);
}
else
{
//metto la & prima delle variabili per indicare che sto effetuando un passaggio di parametri per riferimento (ovvero per indirizzo)
//e non per valore
leggi_matrice(nomefile, matricevip, &R, &C);
stampa_matrice(matricevip, R, C);
}
return 0;
}
void leggi_matrice(const char* nomefile, matrix *m, int *r, int *c)
{
//**matricevip è un doppio puntatore(un puntatore per le righe e uno per le colonne)
char buffer[MAX_C], *res, temp;
int i = 0, j = 0;
FILE *ptrvip;
if((ptrvip=fopen(nomefile, "r"))== NULL)
printf("Impossibile aprire il file %s\n", nomefile);
else
{
printf("File %s letto correttamente!\n\n", nomefile);
//Acquisizione numero di colonne
res = fgets(buffer, MAX_C, ptrvip);
while(res[i] != '\0')
{
*c = *c +1;
i++;
}
C = *c;
//Riposiziono il cursore all'inizio del file
fseek(ptrvip, 0, 0);
//Conto il numero della righe
while(1)
{
res = fgets(buffer, MAX_R, ptrvip);
if(res == NULL)
break;
*r = *r + 1;
}
R = *r;
//Allocazione dinamica della memoria
m = (char**) malloc (*c * sizeof(char*));//alloco lo spazio per le colonne
for(i = 0; i < *c; i++)
m[i] = (char*) malloc (*r * sizeof(char));//alloco lo spazio per le righe
//Riposiziono il cursore all'inizio del file
fseek(ptrvip, 0, 0);
//Caricamento della matrice da file
while(!feof(ptrvip))
{
for(i = 0; i < *r; i++)
for(j = 0; j < *c; j++)
{
fscanf(ptrvip, "%c", &temp);
if(temp != '\0')
m[i][j] = temp;
}
}
fclose(ptrvip);
}
}
void stampa_matrice(matrix *m, int r, int c)
{
printf("\n");
int i,j;
for (i=0;i<r;++i)
{
for (j=0;j<c-1;++j)
printf("%c",m[i][j]);
printf("\n");
}
printf("\n");
}
Domanda: come posso fare senza allocare dinamicamente la matrice in memoria?
Sto cercando la strada più semplice per farlo ma questi puntatori mi mettono il bastone tra le ruote
Ho provato a fare quest'altra prova ma mi da errore quando richiamo le funzioni nel main in cui gli passo la matrice:
codice:
#include <stdio.h>
#include <stdlib.h>
#define MAX_C 50
#define MAX_R 50
int R, C;
void leggi_matrice(const char* nomefile, char mat[][MAX_C]);
void stampa_matrice(char mat [][MAX_C]);
void salva_file(const char* nomefile, char mat [][MAX_C]);
void delete_c(char mat [][MAX_C], int colonna);
void delete_r(char mat [][MAX_C], int riga);
int main(int argc, char *argv[])
{
char tipo;
char matricevip[MAX_R][MAX_C];
int numero;
char* nomefile = argv[1];
if(argc!=2)
{
printf("Numero di argomenti inseriti errato!\n");
exit(EXIT_FAILURE);
}
else
{
leggi_matrice(matricevip, nomefile);
stampa_matrice(matricevip);
}
printf("\n");
printf("Comando: ");
scanf("%c %d", &tipo, &numero);
//La riga che segue serve per togliere l'invio dal buffer
while(tipo != 'x'){
switch(tipo)
{
case 'c':
if(!numero){
printf("Errore: colonna non specificata!\n");
}
else if(numero < 0 || numero > C){
printf("Errore: il numero della colonna specificata eccede la dimenzione max del file!\n");
}
else
{
printf("test_1");
delete_c(matricevip, numero);
printf("Rimossa colonna %d", numero);
stampa_matrice(matricevip);
}
printf("Comando: ");
scanf("%c %d", tipo, &numero);
continue;
case 'r':
if(!numero){
printf("Errore: riga non specificata!\n");
}
else if(numero < 0 ||numero > R){
printf("Errore: il numero della riga specificata eccede la dimenzione max del file!\n");
}
else
{
delete_r(matricevip, numero);
printf("Rimossa riga %d", numero);
stampa_matrice(matricevip);
}
printf("Comando: ");
scanf("%c %d", tipo, &numero);
continue;
case 'q':
salva_file(nomefile, matricevip);
break;
default:
printf("Comando non valido");
exit(EXIT_FAILURE);
break;
}
}
return 0;
}
void leggi_matrice(const char* nomefile, char mat[MAX_R][MAX_C])
{
//**matricevip è un doppio puntatore(un puntatore per le righe e uno per le colonne)
char buffer[MAX_C], *res, temp;
int i = 0, j = 0, R = 0, C = 0;
FILE *ptrvip = fopen(nomefile, "r");
if(nomefile == NULL)
printf("Impossibile aprire il file %s\n", nomefile);
else
{
printf("File %s letto correttamente!\n\n", nomefile);
//Acquisizione numero di colonne
res = fgets(buffer, MAX_C, ptrvip);
while(res[i] != '\0')
{
C = C +1;
i++;
}
//Riposiziono il cursore all'inizio del file
fseek(ptrvip, 0, 0);
//Conto il numero della righe
while(1)
{
res = fgets(buffer, MAX_R, ptrvip);
if(res == NULL)
break;
R = R + 1;
}
//Riposiziono il cursore all'inizio del file
fseek(ptrvip, 0, 0);
//Caricamento della matrice da file
while(!feof(ptrvip))
{
for(i = 0; i < R; i++)
for(j = 0; j < C; j++)
{
fscanf(ptrvip, "%c", &temp);
if(temp != '\0')
mat[i][j] = temp;
}
printf("\n");
}
fclose(ptrvip);
}
}
void stampa_matrice(char mat[MAX_R][MAX_C])
{
printf("\n");
int i,j;
for (i=0;i<R;++i)
{
for (j=0;j<C;++j)
printf("%c", mat[i][j]);
}
printf("\n");
}
void salva_file(const char* nomefile, char mat[MAX_R][MAX_C]){
int i = 0, j = 0;
FILE *ptrvip = fopen(nomefile, "w");
if(nomefile == NULL)
printf("Impossibile aprire il file %s\n", nomefile);
else{
for(i=0; i<R; i++){
for(j=0; j<C; j++)
{
fprintf(ptrvip, "%c\n", mat[i][j]);
}
fprintf(ptrvip, "%c\n", '\n');
}
}
}
void delete_c(char mat[MAX_R][MAX_C], int colonna){
int i,j;
if(colonna == C-1)
C = C - 1;
else{
for(i=0; i<R; i++){
for(j=colonna; j<C; j++)
{
mat[i][j] = mat[i][j+1];
}
}
C = C - 1;
}
printf("La matrice è: \n");
stampa_matrice(mat);
}
void delete_r(char mat[MAX_R][MAX_C], int riga){
int i,j;
if(riga == R-1)
R = R - 1;
else{
for(i=riga; i<R-1; i++){
for(j=0; j<C; j++)
{
mat[i][j] = mat[i+1][j];
}
}
R = R - 1;
}
printf("La matrice è: \n");
stampa_matrice(mat);
}