2011-03-17 8 views
7

Ho circa 500 file HDF5 ciascuno di circa 1,5 GB.Concatena un numero elevato di file HDF5

Ciascuno dei file ha la stessa struttura esatta, ovvero 7 dataset composti (int, doppio, doppio) e numero variabile di campioni.

Ora voglio concatenare tutti questi file concatenando ciascuno dei set di dati in modo che alla fine abbia un singolo file da 750 GB con i miei 7 set di dati.

Attualmente sto facendo funzionare uno script h5py cui:

  • crea un file HDF5 con i giusti set di dati di massimo illimitato
  • aperti in sequenza tutti i file
  • verifica qual è il numero di campioni (come è variabile)
  • ridimensionare il file globale
  • aggiungere i dati

questo ovviamente richiede molte ore, avete un suggerimento per migliorare questo?

Sto lavorando su un cluster, quindi potrei usare HDF5 in parallelo, ma non sono abbastanza bravo nella programmazione C per implementare qualcosa da solo, avrei bisogno di uno strumento già scritto.

+0

Una possibilità è unire coppie di file sul tuo cluster; ridurre il problema a 250 file da 3 GB, quindi a 125 file da 6 GB e così via. Ciò è utile solo se i file parzialmente uniti offrono un risparmio di tempo durante l'unione dei risultati in seguito. – sarnold

+0

@sarnold Sto lavorando su hopper in NERSC, la velocità di I/O teorica è di 25 GB/s, anche il filesystem è completamente parallelo e supporta I/O MPI. –

+0

Stavo pensando di leggere forse 3 o 4 file alla volta e di scriverli tutti insieme, ma la cosa migliore sarebbe un'utilità c che sfrutta in qualche modo l'I/O mpi. –

risposta

8

Ho scoperto che la maggior parte del tempo è stata spesa per ridimensionare il file, poiché stavo ridimensionando ogni fase, quindi ora sto prima andando attraverso tutti i miei file e ottengo la loro lunghezza (è variabile).

Quindi creo il file h5 globale impostando la lunghezza totale sulla somma di tutti i file.

Solo dopo questa fase riempio il file h5 con i dati di tutti i file di piccole dimensioni.

ora occorrono circa 10 secondi per ciascun file, quindi è necessario impiegare meno di 2 ore, mentre prima richiedeva molto di più.

1

Mi viene risposto che questo mi guadagna un badge necro, ma di recente le cose sono migliorate in questo settore.

In Julia ci vogliono alcuni secondi.

  1. Creare un file txt in cui sono elencati tutti i percorsi dei file HDF5 (è possibile utilizzare bash per fare questo in una volta sola, se ci sono un sacco)
  2. In un anello di leggere ogni riga del file txt e utilizzare label$i = h5read(original_filepath$i, "/label")
  3. concat tutte le etichette label = [etichetta $ i]
  4. Poi basta scrivere: h5write(data_file_path, "/label", label)

stesso può essere fatto se si dispone di gruppi o file HDF5 più complicate.

1

La risposta di Ashley ha funzionato bene per me.Ecco un'implementazione di suo suggerimento a Julia:

file di testo Fare l'elenco dei file per concatenare in bash:

ls -rt $somedirectory/$somerootfilename-*.hdf5 >> listofHDF5files.txt 

scrivere uno script julia per concatenare più file in un unico file:

# concatenate_HDF5.jl 
using HDF5 

inputfilepath=ARGS[1] 
outputfilepath=ARGS[2] 

f = open(inputfilepath) 
firstit=true 
data=[] 
for line in eachline(f) 
    r = strip(line, ['\n']) 
    print(r,"\n") 
    datai = h5read(r, "/data") 
    if (firstit) 
     data=datai 
     firstit=false 
    else 
     data=cat(4,data, datai) #In this case concatenating on 4th dimension 
    end 
end 
h5write(outputfilepath, "/data", data) 

Quindi eseguire il file di script sopra utilizzando:

julia concatenate_HDF5.jl listofHDF5files.txt final_concatenated_HDF5.hdf5