-
Notifications
You must be signed in to change notification settings - Fork 258
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Documentation suggestion: recommendations for working with integer NIFTI images #1001
Comments
Hi there! This issue is of great interest to our project (as indicated by the number of pings in the history above). We work with integer-typed images quite frequently (e.g. integer-valued labels for image landmarks, binary masks, etc.). When our integer data arrays are coerced to float via To highlight one of the proposed solutions from the issue description:
Right now, to implement this suggestion, we're considering using a pattern akin to: im.get_fdata().astype(im.header.get_data_dtype()) The idea here being to use this pattern on the very first call to Though, this assumes that the header metadata is truthworthy. I don't know if this is a safe assumption to make... |
I guess we did not get around to writing documentation, so here are some notes:
|
Hi @effigies and @matthew-brett (pinging you both directly, because you've had the most involvement in the relevant bits of the nibabel code).
A colleague of mine, very competent, but fairly new to nibabel and numpy, recently found himself in a very confusing situation, ultimately brought about by the
scl_slope
/scl_inter
rescaling logic baked into nibabel, and I'm wondering if another section should be added to the nibabel documentation which gives recommendations on how to work with NIFTI images of integral type.A full example is given below, but in brief, he was working with a NIFTI1 image of type
int32
, but working withfloat64
arrays in memory. He was repeatedly loading an image in, manipulating it, and saving it back out as anint32
image. After a couple of iterations, the floating point imprecision in thescl_slope
andscl_inter
fields had accumulated enough that the integral values of his image data were no longer being re-constructed, which caused problems when he tried to create and use a binary mask.The problem boils down to a combination of two coding patterns that are in common use:
Using
get_fdata
to retrieve the image data, so that it is always loaded and manipulated asfloat64
, regardless of the storage type.When creating a new image from an existing image (e.g. after some processing step), using the header from the original image to preserve the NIFTI header metadata (not that there's much of use in there, but that's another matter):
Using the above patterns with images of integer type can lead to problems, as demonstrated in the example below. So what I'm wondering is whether a section should be added to the nibabel documentation, with some recommended strategies for working with integral data. I'd be happy to attempt a first pass if you think it's a good idea.
I can think of a few solutions/patterns to avoiding this problem, any of which could be the best approach depending on the situation:
To reproduce the situation that my colleague found himself in:
Example output (note the teensy scaling factor):
The text was updated successfully, but these errors were encountered: