一、 影像组学特征分类
1.1 影像组学特征分类
1.1.1 一阶统计特征
一阶统计特征,反应所测体素的对称性、均匀性以及局部强度分布变化。包括中值,平均值,最小值,最大值,标准差,偏度,峰度等。
1.1.2 形态特征
形态特征,定量描述感兴趣区的几何特性,如肿瘤的表面积、体积、表面积和体积比、球形度、紧凑性和三维直径等,这些特征可以描述肿瘤三维的大小和形态信息。
1.1.3 二阶及高阶纹理特征
此外,还有原始图像或使用不同滤波方法对影像进行滤波后的二阶及高阶纹理特征,这些特征能够反映图像体素灰度之间的空间排列关系。主要包括以下分类。
灰度共生矩阵(GrayLevelCooccurence Matrix,GLCM):反映在给定的方向和距离上体素值出现的概率。
灰度游程长度矩阵(Gray LevelRun Length Matrix,GLRLM):描述相同灰度级的体素在指定方向上连续出现的长度。
灰度尺寸区域矩阵(Gray LevelSize Zone Matrix,GLSZM):量化图像中连续体素值的区域。
**邻域灰度差矩阵(Neighbouring Gray Tone Difference Matrix,NGTDM)😗*量化体素灰度值与特定距离内邻域的平均灰度值之间的差异。
**灰度相关矩阵(Gray Level Dependence Matrix,GLDM)😗*基于体素值测量相邻体素之间的差异。
1.2 影像组学特征研究热点
挖掘与生理、病理的关系,进行解释
二、影像组学特征提取
2.1 pyradiomics安装
安装命令:pip install pyradiomics/conda install pyradiomics
如果遇到未安装pywt库的提示,请安装pywavelets库。
2.2 特征提取实战–一个简单案例
代码;
from radiomics import featureextractorimport osbasePath = "G:\\brain1\\"imageFile =os.path.join(basePath,'brain1_image.nrrd')maskFile = os.path.join(basePath,'brain1_label.nrrd')extractor = featureextractor.RadiomicsFeatureExtractor()featureVector = extractor.execute(imageFile,maskFile)for featureName in featureVector.keys():print("%s : %s" % (featureName,featureVector[featureName]))
结果:
2.3 常用参数设置
代码:
from radiomics import featureextractorimport osimport SimpleITK as sitkbasePath = "G:\\brain1\\"imageFile =os.path.join(basePath,'brain1_image.nrrd')maskFile = os.path.join(basePath,'brain1_label.nrrd')settings = {}settings['binWith'] = 25settings['resamplePixelSpacing'] = [3,3,3] # unit:mm 重采样settings['interpolator'] = sitk.sitkNearestNeighbor #插值方法settings['normalize'] = True # 图像归一化extractor = featureextractor.RadiomicsFeatureExtractor(**settings)featureVector = extractor.execute(imageFile,maskFile)for featureName in featureVector.keys():print("%s : %s" % (featureName,featureVector[featureName]))
SimpleITK中提供的插值方法:
个别特征提取:
extractor.disableAllFeatures()extractor.enableFeaturesByName(firstorder=['Mean', 'Skewness'])featureVector = extractor.execute(imageFile, maskFile)for featureName in featureVector.keys():print("%s: %s" % (featureName, featureVector[featureName]))
diagnostics_Versions_PyRadiomics: 0+unknowndiagnostics_Versions_Numpy: 1.19.2diagnostics_Versions_SimpleITK: 2.0.2diagnostics_Versions_PyWavelet: 1.1.1diagnostics_Versions_Python: 3.8.5diagnostics_Configuration_Settings: {'minimumROIDimensions': 2, 'minimumROISize': None, 'normalize': True, 'normalizeScale': 1, 'removeOutliers': None, 'resampledPixelSpacing': [3, 3, 3], 'interpolator': 1, 'preCrop': False, 'padDistance': 5, 'distances': [1], 'force2D': False, 'force2Ddimension': 0, 'resegmentRange': None, 'label': 1, 'additionalInfo': True, 'binWidth': 25}diagnostics_Configuration_EnabledImageTypes: {'Original': {}}diagnostics_Image-original_Hash: 5c9ce3ca174f0f8324aa4d277e0fef82dc5ac566diagnostics_Image-original_Dimensionality: 3Ddiagnostics_Image-original_Spacing: (0.7812499999999999, 0.7812499999999999, 6.499999999999998)diagnostics_Image-original_Size: (256, 256, 25)diagnostics_Image-original_Mean: 385.6564080810547diagnostics_Image-original_Minimum: 0.0diagnostics_Image-original_Maximum: 3057.0diagnostics_Mask-original_Hash: 9dc2c3137b31fd872997d92c9a92d5178126d9d3diagnostics_Mask-original_Spacing: (0.7812499999999999, 0.7812499999999999, 6.499999999999998)diagnostics_Mask-original_Size: (256, 256, 25)diagnostics_Mask-original_BoundingBox: (162, 84, 11, 47, 70, 7)diagnostics_Mask-original_VoxelNum: 4137diagnostics_Mask-original_VolumeNum: 2diagnostics_Mask-original_CenterOfMassIndex: (186.98549673676578, 106.3562968334542, 14.38917089678511)diagnostics_Mask-original_CenterOfMass: (46.47304432559825, 16.518518098863908, 15.529610829103234)diagnostics_Image-interpolated_Spacing: (3.0, 3.0, 3.0)diagnostics_Image-interpolated_Size: (24, 30, 27)diagnostics_Image-interpolated_Mean: 0.44909917493419343diagnostics_Image-interpolated_Minimum: -0.957997711468711diagnostics_Image-interpolated_Maximum: 5.339121039019602diagnostics_Mask-interpolated_Spacing: (3.0, 3.0, 3.0)diagnostics_Mask-interpolated_Size: (24, 30, 27)diagnostics_Mask-interpolated_BoundingBox: (5, 6, 7, 12, 18, 15)diagnostics_Mask-interpolated_VoxelNum: 641diagnostics_Mask-interpolated_VolumeNum: 2diagnostics_Mask-interpolated_CenterOfMassIndex: (11.257410296411857, 11.249609984399376, 14.798751950078003)diagnostics_Mask-interpolated_CenterOfMass: (46.27223088923557, 16.751170046801853, 15.646255850234056)diagnostics_Mask-interpolated_Mean: 1.0639000504485487diagnostics_Mask-interpolated_Minimum: 0.2964578976029255diagnostics_Mask-interpolated_Maximum: 2.072568314407322original_firstorder_Mean: 1.0639000504485487original_firstorder_Skewness: 0.44927279398674264
特征类别选择:
extractor.disableAllFeatures() # 关闭所有特征extractor.enableFeatureClassByName('glrlm')extractor.enableFeatureClassByName('glcm')featureVector = extractor.execute(imageFile, maskFile)for featureName in featureVector.keys():print("%s: %s" % (featureName, featureVector[featureName]))
滤波器选择:
extractor.enableImageTypes(Original={}, LoG={"sigma" : [4.0]}, Wavelet={})featureVector = extractor.execute(imageFile, maskFile)for featureName in featureVector.keys():print("%s: %s" % (featureName, featureVector[featureName]))
三、影像组学特征批量提取
import pandas as pdbasePath = '/Users/lirenyuan/Desktop/RadiomicsWorld/course/data/featureExtraction'folders = os.listdir(basePath)print(folders)
df = pd.DataFrame()extractor = featureextractor.RadiomicsFeatureExtractor()for folder in folders:files = os.listdir(os.path.join(basePath,folder))print(files)for file in files:if file.endswith('image.nrrd'):imageFile = os.path.join(basePath,folder,file)if file.endswith('label.nrrd'):maskFile = os.path.join(basePath,folder,file)#print(imageFile, maskFile)featureVector = extractor.execute(imageFile, maskFile)df_new = pd.DataFrame.from_dict(featureVector.values()).Tdf_new.columns = featureVector.keys()df = pd.concat([df,df_new])df.to_excel(os.path.join(basePath,'results.xlsx'))