Uncompress previously compressed objects in files (trees)

Hi there,

is there any way (preferably in a form of an “out-of-box” tool) in ROOT I/O to switch back and forth between compressed and uncompressed version of (objects within a) file. If no such tool exists then how this can be done at a level of the API in a general, application-independent way? Anyone has a recipie?

[ Another thing to mention is that my objects are stored in TTree-s. ]

Here is what I mean. Imagine I create a new file with the compressionLevel set to 1 (“minimal but fast compression” as per ROOT documentation). Then I store my objects in the file. Later I decide to convert the objects into the non-compressed form. Clearly I could do the same thing by writing a (problem) domain-specific tool knownig about my specific persistent classes, however anyone understands that this thing would be unmaintaiable in the long run.

A reason why I’m asking this question is that even the minimal compression may cost me x2 (sometimes up to x3) slowdown in terms of an application performance (depending on how big are the objects, and how I access them from TTree-s: sequentially or randomly). In some occasions I’d be willing to sacrifice the disk space in favor of getting the maximum performance out of my application.


Hi Igor,

In the CVS version, I have modified TTree::CloneTree such that
the cloned Tree has the compression factor of the destination file.
CloneTree is used by TTree::CopyTree and TChain::Merge.

I have also modified the utility $ROOTSYS/bin/hadd

[code]It is now possible to specify the compression factor of the destination file.
hadd -f result.root file1.root file2.root (case 1)
hadd -f0 result.root file1.root file2.root (case 2)
hadd -f6 result.root file1.root (case 3)

In case 1, result.root will have a compression factor 1 (default)
In case 2, result.root will not be compressed
In case 3, result.root will be a copy of file1.root but with compression 6

This provides a convenient way to copy a compressed file in a non-compressed file or vice-versa



I intervene to this old post to ask my question: I have used the suggested "hadd -f0" way to decompress on root file of mine. It perfectly works. But when the file become too big I get the error

Error in TBranchElement::Fill: Failed filling branch:edepScint_hits, nbytes=-1
Error in TTree::Fill: Failed filling branch:nT.edepScint_hits, nbytes=-1, entry=998945
This error is symptomatic of a Tree created as a memory-resident Tree
Instead of doing:
TTree *T = new TTree(…)
TFile *f = new TFile(…)
you should do:
TFile *f = new TFile(…)
TTree *T = new TTree(…)

Does the problem depend on the hadd implementation or on the way my original root file was created?
How to solve?



Hi Maddalena,

This could come from either the physical disk being filled or it could be that one of the individual buffer is growing past 1Gb … or something else. It could indeed also be an issue with hadd itself (you do not mention which version of ROOT you are using).

If after trying v6.04/02 or v5.34/32, you still see the problem please send us enough information (likely the problematic file) to reproduce the problem.