Wie mehrdimensionale Arrays handhaben?

04/09/2008 - 00:23 von Roland Damm | Report spam
Moin,

meine Frage richtet sich an die, die sowas vielleicht öfters
machen, und zwar: Wie macht man das üblicherweise/am
elegantesten?

Problem: Wàrend der Laufzeit eines Programms wird ermittelt, wie
groß ein Array, sagen wir
int a[N][M]
sein muss, N und M werden also erst ermittlet.

Nun ist ja IMO irgendwann mal von Compilerspezifischen
Besonderheiten zum Standard geworden, dass folgende
Funktionsdefinition erlaubt ist:

int func(int a[N][M], int N, int M)
{.}

Ich kann also z.B. scheiben:
int main()
{

p=malloc(sizeof(int)*N*M);
x=func(p,N,M);

}

Richtig?

Kann man aber etwas in der Art machen, welches ich mal so
beschreiben würde (was natürlich kein gültiger C-Code ist):
(N, M sind mit richtigen Werten belegt)

int a[N][M] = malloc(sizeof(int)*N*M);
a[3][7] = 6;


Will sagen: So dass ich auch in der Funktion, in der der Array
erst angelegt wird, ich schon die Schreibweise mit a[i][j]
verwenden kann?
Alternativ könnte man ja
a[i*N+j] = ...
verwenden (bin mir unsicher mit der Reihenfolge der Indizes), nur
finde ich diese Schreibweise irgendwie unschön.

Könnte man casten:

p=malloc(sizeof(int)*N*M);
((int[N][M])p)[i][j] = 45;

? Die Schreibweise ist sicher aber auch nicht sehr ansehnlich

Wie macht man sowas normalerweise?

CU Rollo
 

Lesen sie die antworten

#1 Alexander Bartolich
04/09/2008 - 00:55 | Warnen spam
Roland Damm schrieb:
[...]
meine Frage richtet sich an die, die sowas vielleicht öfters
machen, und zwar: Wie macht man das üblicherweise/am
elegantesten?



Am elegantesten geht das über ein Feld von Zeigern.

Problem: Wàrend der Laufzeit eines Programms wird ermittelt, wie
groß ein Array, sagen wir
int a[N][M]
sein muss, N und M werden also erst ermittlet.



Bei einer Deklaration wie

int a[N][M];

landen N und M als Konstanten im Code. Es werden N * M Elemente reser-
viert und die Adressberechnung geht davon aus, dass &a[1][0] genau
M Elemente hinter &a[0][0] liegt.

Das funktioniert im klassischen C aber wirklich nur mit Konstanten.

[...]
int func(int a[N][M], int N, int M)
{.}



Bei einer Deklaration wie

int func(int a[N][M]);

müssen N und M Konstanten sein.

Wenn du natürlich (TM) aussehende Syntax für den Feldzugriff haben
willst, geht das so

int func(int** b, int N, int M)
{
int x = b[1][0];

Der Nachteil ist, dass Zugriffe
1. indirekt über Zeiger gehen (anstatt durch Multiplikation)
2. diese zusàtzlichen Zeiger natürlich zusàtzlichen Speicher brauchen
3. diese Zeiger auch korrekt initialisiert werden müssen

Die Speicher-effiziente Methode sieht grundsàtzlich so aus:

int func(int* b, int N, int M)
{
int x = b[1 * M + 0];

Die Multiplikation làsst sich durch ein Macro verstecken, allerdings
sieht das dann eher wie Fortran aus.

int func(int* b, int N, int M)
{
#define B(n,m) b[(n) * N + (m)]

int x = B(1,0)

usingwhitespaceisracism

Ähnliche fragen