4
votes

I'm working on some chest scans from the LIDC database, I am trying to apply iterative (optimal) thresholding on them to extract the lung area. Many researchers use an initial threshold of (or around -500) although they use the same database. I quote

The HU values in each Lung CT scan range from +2000 to -2000HU. The lung area is a low density area ranging from -1000 to -450HU, called non-body area.

I'm using Matlab for that purpose, my scans have different ranges and the problem is, non of them has the lung area under the range of (-1000 to -450HU) (or at least as far as I know), all of the areas ranges are from 0 and above except the area of the rim (the area produced by the scan machine).

How can I make those scans have normal ranges (shift the hounsfield units or something else) for me to work normally on with a lung window of (width of 1500, and center of -500)?

Example of a scan: Here's a Dicom slice with the properties below:

  • Widow Center: -600
  • Window Width: 1600
  • Rescale Intercept: -1024
  • min value: -1024
  • max value: +4095

I'm using the function dicomreadVolume to read the scans:

% Read the scan volume: (the result will be in 4D )
[V,s,d] = dicomreadVolume(fullfile('scan folder...'));

% Convert into 3D:
V2 = squeeze(V);

% display the slice number 83
imtool(V2(:, :, 83));

enter image description here enter image description here

2
Does the database come with calibration data? The CT scanner must be calibrated w.r.t. water to convert the scanner output to Hounsfield units.Cris Luengo
@CrisLuengo I can't find any file that is related to water calibration or is it included in the metadata of the Dicom files? this is the website of the database: wiki.cancerimagingarchive.net/display/Public/LIDC-IDRIZSmain
I suspect simple linear transformation may do what you are asking, but I don't understand the values you posted. Can you make a small list of source value and destination value (or source range, destination range, source center, destination center). Upload some input data and expected output so I can test my answer.Rotem
For shifting range of x from [310, 860] to [-1000, -450], use: y = (x-310)/(860- 310)*(-450 - (-1000)) - 1000Rotem
Can you please post an input image, so I can post a real answer (if I can)Rotem

2 Answers

3
votes

Looking at the histograms, it seems that the function dicomreadVolume() does not take Rescale Slope and Rescale Intercept into account. I suppose the Pixel Representation (0028, 0103) of the image is 0 (= unsigned integer).

So in fact, you are not dealing with HU in Matlab, you are rather dealing with raw pixel values. The transformation to HU is achieved by applying the linear transformation to each pixel. The linear transformation is defined by Rescale Intercept (0028,1052) and Rescale Slope (0028,1053):

<pixel value in HU> := RescaleIntercept + RescaleSlope * <untransformed pixel value> 

I would strongly recommend to go that way rather than shifting the range by some random value obtained from one particular image. This is because HU are valid across all images of the scan.

1
votes

Adding to the answer of kritzel_sw, you can gain access to any rescale slope and rescale intercept in MATLAB by using the dicominfo function, which provides access to most dicom tags:

files = fullfile('scan folder...')

% Read all meta information (dicom tags)
metaInfo = dicominfo(files{1});

% Read the scan volume: (the result will be in 4D )
[V,s,d] = dicomreadVolume();
V = metaInfo.RescaleIntercept + metaInfo.RescaleSlope * squeeze(V); 

This will rescale the pixel values correctly. The rescale intercept and slope should be the same for a consistent dicom stack, but if you want to be sure you could iterate over all slices (files) and compare the values or apply them on the according z slice of the volume V.