Skip navigation

SimpleITK B-Spline regisztráció

Jellemzők

Nemlináris regisztráció programozott megoldására az ITK/SimpleITK függvénykönyvtárak használata javasolt. Ezek számos transzformációt és optimalizáló módszer magukban foglalnak. Objektum felépítésük könnyen paraméterezhető megoldásokhoz vezet. A példánkban a SimpleITK_BSpline mappában található 2D B-Spline regisztráció felépítését mutatjuk be.

sitk_reg_bspline1.py példaprogram

Szükséges fájlok importálása.

import SimpleITK as sitk
import sys

Megadunk egy függvényt, amely minden iterációs lépésben kiértékelődik majd. Így lehetőségünk van például kiírni a konzolra az iterációszámot, valamint az aktuális hasonlósági értéket. Akár a deformált képet is előállíthatnánk és a bázisképre vetíthetnénk, hogy vizuálisan is követni tudjuk a regisztráció menetét. Gyakorlásként oldjuk is meg!

# Print iteration info to console
def command_iteration(method) :
    print("{0:3} = {1:10.5f}".format(method.GetOptimizerIteration(), method.GetMetricValue()))

A program parancssori paraméterként várja a fájlneveket. Az első a báziskép, a második a regisztrálandó. Harmadikként az eredmény kép fájlnevét, utolsóként az optimális B-Spline transzformáció paramétereit tartalmazó szöveges fájl nevét adhatjuk át.

A PyCharm környezetben az alábbi módon állíthatunk be rögzített parancssori paramétereket. Ha még nem tettük, akkor futtasuk a programot. Hibaüzenetet fogunk kapni, de a PyCharm létrehoz egy futtatási konfigurációs fájlt a programhoz, amit ígytovább tudunk szerkeszteni a Run / Edit Configurations... menüponttal. A bal oldali panelen a Python programunk legyen kiválasztva. A jobb oldali panelen a Configurations mezőben adjuk meg az értékeket, például: o1.png o2.png o1_o2.png o1_o2_transform.txt

Ha nincs elegendő parancssori paraméter, hibaüzenettel kilépünk.

if len(sys.argv) < 4:
    print("Usage: {0} <fixedImageFilter> <movingImageFile> <outputImageFile> <outputTransformFile>".format(sys.argv[0]))
    sys.exit(1)

Képek beolvasása a SimpleITK függvényével. A B-Spline transzformációhoz lebegőpontos típusra kell alakítanunk őket.

# Reading images
fixed = sitk.ReadImage(sys.argv[1], sitk.sitkFloat32)
moving = sitk.ReadImage(sys.argv[2], sitk.sitkFloat32)

B-Spline transzformáció kezdeti paramétereinek előállítása csupa 0 értékkel. A transfromDomainMeshSize értéke esetünkben [8, 8] lesz, vagyis minden dimenzió mentén 8 foltot kérünk. Ez a képet 64 foltra osztja fel. A köbös B-Spline esetén egy képen kívüli, a belsőkkel egyező méretű folt-sáv is hozzárendelésre kerül, így 10x10 folt lesz. A 10 folt sarkait 11 ponttal adhatjuk meg egy irányban. Az összes paraméter száma így 11x11x2 = 242 lesz. (Minden folt pont X- és Y-koordinátával rendelkezik.) A B-Spline a belső területeken a közelben található rácspontok elmozdulási vektorainak súlyozott összegével számol.

transfromDomainMeshSize = [8] * moving.GetDimension()
tx = sitk.BSplineTransformInitializer(fixed, transfromDomainMeshSize)

print('Domain mesh size: ', transfromDomainMeshSize)
print("Initial Parameters:")
print(tx.GetParameters())
print(len(tx.GetParameters()))

Regisztrációs műveletsor felépítése. Az R objektum lesz a központi elem. Ehhez a korrelációt állítjuk be hasonlósági mértékként. Optimalizálóként a Limited memory Broyden Fletcher Goldfarb Shannon minimization with simple bounds módszert használjuk, amely alkalmas a nagy paraméterszámú optimalizáló feladat megoldására. A kezdeti transzformáció az előzőleg létrehozott tx lesz. Lineáris interpolációt választunk a transzformáció végrehajtásához. Végül az iterációk figyelésére beállítjuk az előzőleg definiált command_iteration függvényünket.

# Setting up registration pipeline

R = sitk.ImageRegistrationMethod()
R.SetMetricAsCorrelation()

R.SetOptimizerAsLBFGSB(gradientConvergenceTolerance=1e-5,
    numberOfIterations=100,
    maximumNumberOfCorrections=5,
    maximumNumberOfFunctionEvaluations=1000,
    costFunctionConvergenceFactor=1e+7)
R.SetInitialTransform(tx, True)
R.SetInterpolator(sitk.sitkLinear)

R.AddCommand(sitk.sitkIterationEvent, lambda: command_iteration(R))

A regisztrációs folyamat indítása.

# Execute registration and print result
outTx = R.Execute(fixed, moving)

Erdmény kiírása a konzolra és a paraméter szövegfájlba.

print("-------")
print(outTx)
print("Optimizer stop condition: {0}".format(R.GetOptimizerStopConditionDescription()))
print(" Iteration: {0}".format(R.GetOptimizerIteration()))
print(" Metric value: {0}".format(R.GetMetricValue()))

# Save transform and transformed result
sitk.WriteTransform(outTx, sys.argv[4])

Regisztrálandó kép újramintavételezése az optimális transzformációval a referenciakép rácsán, és fájlba írása. PNG exportáláshoz a sitkFloat32 típusú képet sitkUInt8 típusúvá kell alakítani!

resampler = sitk.ResampleImageFilter()
resampler.SetReferenceImage(fixed)
resampler.SetInterpolator(sitk.sitkLinear)
resampler.SetDefaultPixelValue(0)
resampler.SetTransform(outTx)

out = resampler.Execute(moving)
# PNG can handle unsigned integer data
outu8 = sitk.Cast(sitk.RescaleIntensity(out), sitk.sitkUInt8)
sitk.WriteImage(outu8, sys.argv[3])

Eredmény

o1.png és o2.png bemeneti képek. A második az első kép mesterségesen, TPS pontpár-alapú transzformációval deformált változata.

 

B-Spline regisztráció eredménye. Csak kisebb mértékű eltérés marad a képek között.

Az optimális transzformáció paraméterei fájlba írás után.

#Insight Transform File V1.0
#Transform 0
Transform: BSplineTransform_double_2_2
Parameters: -0.000006181409036074943 0.0009446875191276538 0.009304261442749448 0.0106174231680152 0.00597301315061564 -0.0054049695469353225 -0.008151408167367768 0.005968013400893738 0.007054429424367892 0.0011750647035260432 0.000010885941363349114 0.00011919878413543292 0.041377431359054626 0.14111260427061142 -0.7335930116529213 -0.46295062624316885 -2.0239803356270616 0.4320974024687678 0.1097066336776671 0.0012356753922817076 0.013954676405482107 0.0004255387103683141 0.002044063379350757 0.30600828339678043 -1.5595555671269001 -1.5754791299475577 -0.04572986916717308 -0.04930100834189076 1.7370533623485347 -5.110076583039412 0.5102671262034982 0.002680093353655522 0.0029952119818523575 0.004047303083045507 0.5745720162874431 -4.750101855531865 4.423830942091019 -5.920701535938477 10.776668817646815 3.757164496707265 -1.3307648952798325 2.731569684455748 -0.17971378712648095 0.0016760817148508507 -0.0006565195875003274 0.32927011268937667 0.3826702936672577 -2.118936580514546 3.426109736140494 6.384656534556618 3.4952530186903994 -4.917619180437456 3.7805021750727192 0.16577089576666681 0.004802138055492661 -0.005822455529372806 0.3502048016248168 -0.5675847486187505 4.483819359823833 -21.402213272355358 10.831394525799245 8.699112679718512 -0.1644736323296632 -1.5483629374787569 0.8880541886528945 0.010054749655744539 -0.00017329313899737308 1.3726924039016717 0.8090203774934479 -0.2143913768523862 -8.39899660205611 10.91213122207196 -0.7520140080331246 -6.197660178654486 1.3026223502831265 0.939031615250807 0.006797728414523409 0.001345760010888262 0.35097482638828037 -12.871416128988013 -7.138772453737275 -0.00647760480481107 0.16168079019809894 -5.118246817226606 -21.851060483054038 6.662572521514704 0.31490484302943833 0.005366418344229858 0.0009504311323777397 0.15132165971205974 2.0850416854340663 4.55577363634184 5.786084177701695 1.4814805206143513 -1.8694242359083586 11.443120824981863 1.733208177874602 0.06637429425894195 0.0025832731160110637 0.00036146123966132777 0.04636754864846894 0.16634018414434407 -0.06865878047698872 5.174118209619238 1.7926370021667577 -2.3099811931802225 -0.1722820055605157 -0.012712985268170019 0.034322986221727865 0.0013484951843741012 0.000026658528287198293 0.0032150961987736757 0.012110714847724979 0.012969470805651839 0.020408053335653344 0.020311561336042998 0.014958176615664027 0.0010699475631892 0.0024378685946170233 0.005418298090943197 0.0001686742773021436 0.000015208177916518775 0.0012813608328408064 -0.013366478119280595 -0.04233866964189054 -0.004927683212582804 0.006083812549467001 -0.0010226419981017422 0.013302284100319197 0.0072661630486037 -0.000012358777312399044 -0.000004279789943924668 0.0003366357686728326 0.04260894452407288 -0.3574668638217702 1.3340923618191707 -0.6745949432959725 -6.513946001102432 -1.1050710864274798 0.2514446995234208 0.5220576910613292 0.0795293270799225 0.0005583924280139576 0.0013912835537221316 0.23350084438834115 -2.901595189246215 3.9777816621449915 -0.9520032867271664 1.5467759374702343 3.5085817518098747 -9.172770215725446 3.00711005357787 0.5648599017806193 0.004262604496836198 0.0004913049951827358 0.08442967598849246 -3.0900133906044824 1.806894350657128 -8.460765124112248 23.178946829954416 15.267153176864953 -8.979823227035297 4.273742540677973 0.521698429491369 0.003683188085092587 -0.003372586776093042 -0.19119099552717225 3.476278618932995 -1.2982591207114866 4.002079917254331 -0.12688361147561097 -2.625889286986326 1.1665133823628049 0.6276210737093664 0.758036852736279 0.004926729829387497 -0.0035513476894765915 0.1905151447644222 0.1020040185100732 -0.8546340890791847 -9.878369795879077 6.3042211931792504 8.856024572267081 -1.7358066645924977 1.18527540574508 0.4020558332874446 0.005264271453672915 -0.000612345959880195 0.0719414720342891 -0.3662364384211877 7.236175288332933 -14.694712183982281 12.325058705459641 -0.5100405127467201 -6.799330239207616 1.0559415762838826 -0.30528139691349065 0.0018168348550102488 -0.00049795753524497 -0.0953848304387149 5.882900246324834 14.248541705018416 -14.850794732825143 -2.213783214791657 -6.021618949236888 -23.734878368086612 4.509190708885911 0.23607348409520304 0.0012154668470485482 -0.0005145613727698769 -0.0878797671571098 -2.4919623977418883 0.6564717719920742 -13.97847547800292 -2.247169183439711 6.123547269376987 4.343400354724838 1.9704613923359444 0.14967272517866906 0.0005414756769512206 -0.00023949884698790485 -0.035583508858765524 -0.17952454525169645 0.7400714133542274 -5.667571002243237 3.5871304804368647 2.3249073434013527 -0.07857693737844056 0.13271710449671062 -0.016571384133021186 -0.0007127000332719846 -0.000023215977775353 -0.003899072558292615 -0.021682208351637262 -0.034378962654368746 -0.022790045684229994 0.0025377734417537973 0.0001917330775714968 -0.0037844151314686903 -0.018412087413634034 -0.010522757582857574 -0.00018891196693385267
FixedParameters: 11 11 -32.65625 -32.65625 32.03125 32.03125 1 0 0 1

Feladatok

  • Vetítsünk a B-Spline felosztásnak megfelelő rácsot a mozgó képre, hogy a deformáció hatását jobban lássuk!
  • A command_iteration() függvényben állítsuk elő az aktuális iteráció transzformációjának megfelelő deformált képet, és mentsük el önálló fájlba! A fájlnévben jelenjen meg az iteráció száma is, aminek segítségével külső programmal animációs videót készíthetünk.
  • Módosítsunk az egyes keresési paramétereken és a B-Spline felosztás méretén, valamint teszteljük a hatásukat!
  • Keressünk rá a SimpleITK oldalon az ImageRegistrationMethod osztály dokumentációjára, és válasszunk más hasonlósági mértékeket és optimalizáló módszereket! Teszteljük őket!
  • Próbáljuk ki a módszert a smooth_square.pngsmooth_circle.png képpára is, mindkét irányban!
  • Keressünk más képpárokat, amin tesztelhető a módszer!