2013-04-15 5 views
8

Non è così sicuro di come fare questa domanda, ma ho 2 modi (finora) per una matrice di ricercaMatrice seghettata contro un grande array?

Opzione 1 è:

bool[][][] myJaggegArray; 

myJaggegArray = new bool[120][][]; 
for (int i = 0; i < 120; ++i) 
{ 
    if ((i & 0x88) == 0) 
    { 
    //only 64 will be set 
    myJaggegArray[i] = new bool[120][]; 
    for (int j = 0; j < 120; ++j) 
    { 
     if ((j & 0x88) == 0) 
     { 
     //only 64 will be set 
     myJaggegArray[i][j] = new bool[60]; 
     } 
    } 
    } 
} 

Opzione 2 è:

bool[] myArray; 
//    [998520] 
myArray = new bool[(120 | (120 << 7) | (60 << 14))]; 

Entrambe le modalità funzionano bene, ma c'è un altro (migliore) modo di fare una ricerca veloce e quale scegliereste se la velocità/prestazioni è ciò che importa?

Questo sarebbe utilizzato in un chessboard implementation (0x88) e soprattutto è

[from][to][dataX] per opzione 1

[(from | (to << 7) | (dataX << 14))] per opzione 2

+3

Prenderò qualsiasi opzione sia più facile da usare e da leggere. Puoi sempre ottimizzare in un secondo momento, quando il tuo codice è finito e pensi che dovrebbe essere più veloce di quello che è già. – Nolonar

+0

@Nolonar, infatti, sono al punto ora – Fredou

+0

Vorrei utilizzare un array di grandi dimensioni con un metodo getter con tutti e tre i parametri. Entrambi veloci, leggibili e consentono semplici modifiche future. – Dariusz

risposta

2

suggerirei utilizza uno vasta gamma, a causa dei vantaggi di avere una grande blocco di memoria, ma vorrei anche incoraggiare la scrittura di un accessorio speciale per quella matrice.

class MyCustomDataStore 
{ 
    bool[] array; 
    int sizex, sizey, sizez; 

    MyCustomDataStore(int x, int y, int z) { 
    array=new bool[x*y*z]; 
    this.sizex = x; 
    this.sizey = y; 
    this.sizez = z; 
    } 

    bool get(int px, int py, int pz) { 
    // change the order in whatever way you iterate 
    return array [ px*sizex*sizey + py*sizey + pz ]; 
    } 

} 
+0

è più facile da leggere ma guardando il codice IL (a meno che il jitter non faccia l'inlining) questo non si inline e costano molto mentre si trovano in un grande loop. – Fredou

+0

Concordato, a meno che la chiamata alla funzione non sia in linea può renderla molto meno efficiente. Forse contrassegnare il metodo get 'sealed' può migliorare le possibilità. – Dariusz

+0

quick note, 'x * y * z' e' px * sizex * sizey + py * sizey + pz' è sbagliato, dovrebbe essere '(x | (y << 7) | (z << 14))' per entrambi senza tenerli nella variabile locale. – Fredou

1

Ho appena aggiorno soluzione dariusz con una serie di lunghi per z-dimensione < = 64

EDIT2: aggiornato per '< <' versione, dimensione fissa per 128x128x64

class MyCustomDataStore 
{ 
    long[] array; 

    MyCustomDataStore() 
    { 
      array = new long[128 | 128 << 7]; 
    } 

    bool get(int px, int py, int pz) 
    { 
      return (array[px | (py << 7)] & (1 << pz)) == 0; 
    } 

    void set(int px, int py, int pz, bool val) 
    { 
      long mask = (1 << pz); 
      int index = px | (py << 7); 
      if (val) 
      { 
       array[index] |= mask; 
      } 
      else 
      { 
       array[index] &= ~mask; 
      } 
    } 
} 

modifica : test delle prestazioni: utilizzato 100 volte 128x128x64 riempire e leggere

long: 9885ms, 132096B 
bool: 9740ms, 1065088B 
+0

Proverò in modo definitivo questa stasera – Fredou

+0

una nota veloce come ho detto per la soluzione di dariusz, facendo 120 * 120 * 60 quindi usando lo stesso per leggere il valore è sbagliato per quello che ho detto, dovrebbe essere basato su '(x | (y << 7) | (z << 14)) ' – Fredou

+0

ho appena provato e rende tutto un po 'più lento di una matrice di bool – Fredou