Tutoriel 2: lancer vos traitements en batch

Transcription

Tutoriel 2: lancer vos traitements en batch
Tutoriel 2: lancer vos
traitements en batch
Si vous avez besoin de réaliser une série de traitements, sans interaction utilisateur, sur
une série d’images, la programmation batch est particulièrement adaptée.
Vous devez pour cela restaurer ENVI en mode batch (aucune interface ENVI
n’apparaîtra), afin d’avoir accès à toutes les routines ENVI. Utilisez maintenant ENVI
comme une simple librairie de traitements !
Introduction . . . . . . . . . . . . . . . . . . . . . . . . . . . . 2
Les grandes étapes d’un traitement batch . . . 2
FID, DIMS et POS . . . . . . . . . . . . . . . . . . . . . . . . 3
Exemple 1: appliquer un filtre à une série
d’images . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 4
Exemple 2: rajouter de nouveaux traitements et
créer un fichier log . . . . . . . . . . . . . . . . . . . . . . 5
1
2
Tutoriel 2: lancer vos traitements en batch
Introduction
Pour débuter, nous allons reprendre un exemple simple du tutoriel 1: l’application d’un
filtre de détection de contours, SOBEL, à une série d’image situées dans un répertoire.
Les images filtrées ainsi créées seront sauvegardées dans un répertoire de sortie.
Ensuite, ce tutoriel vous montrera comment simplement rajouter de nouveaux
traitements comme la réalisation d’une classification non supervisées, l’application d’un
filtrage majoritaire, etc.
Nous allons écrire les différents codes de nos traitements batch dans une session IDL
simple (elle se reconnait au prompt IDL>).
Les grandes étapes d’un traitement batch
Le schéma ci-dessous montre les principales instructions pour créer une routine de
traitement simple en mode batch :
Figure 2-1. Instructions principales pour créer un traitement batch
ENVI, RESTORE_BASE_SAVE_FILES
Restaurer ENVI en mode
ENVI_BATCH_INIT
batch
Ouverture de l’image à
traiter (non-interactif)
ENVI_OPEN_FILE, filename, R_FID=fid
IF (fid EQ -1) THEN BEGIN
ENVI_BATCH_EXIT
RETURN
ENDIF
(ENVI_OPEN_DATA_FILE pour un format externe)
Récupération d’infos sur
l’image
ENVI_FILE_QUERY, fid, NS=ns, NL=nl, NB=nb, ...$
Application d’un
traitement et sauvegarde
de l’image produite
ENVI_DOIT, ’..’, FID=fid,DIMS=dims,POS=pos,$
R_FID=r_fid, OUT_NAME=...
(ou toute autre routine de traitement ENVI)
Fermeture du mode
batch ENVI
ENVI_BATCH_EXIT
Tutoriel 2: lancer vos traitements en batch
3
FID, DIMS et POS
Dès que vous commencerez à écrire vos propres routines de traitements avec la librairie
ENVI, vous constaterez que trois variables reviennent sytématiquement:
FID (File Identifier)
Il s’agit d’un entier long.
Les entrées/Sorties dans ENVI ne fonctionnent pas de la même manière que dans IDL.
IDL utilise des LUN (Logical Unit Number) et ENVI des FID (File ID).
Dans IDL, l'utilisateur doit gérer les E/S en obtenant une unité logique (à l'ouverture du
fichier) et ensuite en utilisant des routines du type READ/WRITE.
Dans ENVI, toutes les E/S sont contrôlées en interne . L'utilisateur ne va pas utiliser des
routines telles que OPENR, OPENW, etc. mais plutôt des routines de lecture spécifiques
d'ENVI et qui retourneront un identifiant sur le fichier. Cet identifiant de fichier devra
par contre être communiqué à chacune des routines de traitement. Avec cette méthode,
l'utilisateur peut ouvrir autant de fichiers qu'il le souhaite.
Les FIDs peuvent être de trois types:
FID: un FID correspondant à une image d’entrée.
R_FID (Returned FID) : si la routine de traitement aboutit à la création d'une nouvelle
image, un FID est retourné.
M_FID (Mask FID) : permet de spécifier le fichier à utiliser comme masque.
Un FID, R_FID ou M_FID est stocké sous forme d’un entier long.
DIMS: sous-échantillage spatial
La variable DIMS définit un sous-ensemble spatial à utiliser par la routine (utiliser ce
mot-clef même si toute l'image est à traiter).
Table 2-1. Signification des 5 valeurs de DIMS
index
exemple
signification
0
-1L
Pointeur sur une région d’intérêt qui définirait un sousensemble spatial. Si aucune, indiquer -1.
1
0
Colonne de départ (en index de position)
2
ns-1
Colonne de fin (en index de position)
3
0
Ligne de départ (en index de position)
4
nl-1
Ligne de départ (en index de position)
La variable DIMS est codée sous la forme d’un tableau de 5 entiers longs.
4
Tutoriel 2: lancer vos traitements en batch
POS: sous-échantillonage spectral
La variable POS définit un sous-ensemble spectral. Cela consiste à indiquer les index des
bandes sur lesquelles effectuer le traitement (il s’agit d’index de position).
La variable POS est codée sous la forme d’un tableau de N entiers longs, N ne pouvant
pas dépasser le nombre de bandes du fichier.
Exemple 1: appliquer un filtre à une série d’images
La technique utilisée pour appliquer le filtre de SOBEL sur chaque image, est d’utiliser la
routine ENVI équivalente à l’outil Band Math interactif: ENVI_DOIT, ’MATH_DOIT’ en
spécifiant ’SOBEL(b1)’ comme expression (mot-clef EXP). Pour simplifier l’exercice, nous
appliquerons le filtre que sur la première bande du fichier.
Ils existent d’autres solutions pour effectuer ce traitement, mais nous ne les verrons pas
dans ce tutoriel.
batch_processes1 (batch_processes1.pro)
PRO batch_processes1, inputRep, outputRep
COMPILE_OPT idl2
;; Test repertoire de sortie (contiendra les images traitees)
stack = SCOPE_TRACEBACK(/STRUCTURE)
sourceDir = FILE_DIRNAME((stack[N_ELEMENTS(stack)-1]).filename,$
/MARK_DIRECTORY)
IF N_ELEMENTS(outputRep) EQ 0 || ~FILE_TEST(outputRep) $
THEN outputRep = sourceDir
;; Test repertoire d’entree (contient les images a traiter)
default = FILEPATH('', ROOT_DIR=!DIR, $
SUBDIRECTORY=['products','envi42','data'])
IF N_ELEMENTS(inputRep) EQ 0 || ~FILE_TEST(inputRep) $
THEN inputRep = default
;; Restaurer ENVI en mode batch
ENVI, /RESTORE_BASE_SAVE_FILES
ENVI_BATCH_INIT
;; Rechercher tous les fichiers ENVI situes
;; dans le repertoire d'entree
imgFilepath = FILE_SEARCH(inputRep, '*.img', COUNT=nbFiles)
FOR i=0, nbFiles-1 DO BEGIN
;; Lire l'image et recuperer le FID
ENVI_OPEN_FILE, imgFilepath[i], R_FID=fid
IF (fid EQ -1) THEN BEGIN
Tutoriel 2: lancer vos traitements en batch
5
CONTINUE ;on passe au fichier suivant
ENDIF
;; Infos sur le fichier
ENVI_FILE_QUERY, fid, DIMS=dims, NL=nl, NS=ns, NB=nb
;; Appliquer un filtre de SOBEL sur la 1ere bande
;; Sauvegarder l'image filtree
ENVI_DOIT, 'MATH_DOIT', EXP='SOBEL(b1)', $
FID=[fid], DIMS=dims, POS=[0], $
OUT_NAME=outputRep+$
FILE_BASENAME(imgFilepath[i], '.img')+ '_sobel.img'
ENDFOR
;; Fermer le mode batch
ENVI_BATCH_EXIT
END
Exemple 2: rajouter de nouveaux traitements et créer
un fichier log
Création d’un fichier log
Pour créer un fichier log (pour contenir les éventuelles erreurs survenues au cours du
traitement batch et/ou pour simplement retracer l’avancement des traitements), il suffit
de rajouter, au niveau de la procédure BATCH_INIT, les mots-clefs suivants:
[...]
ENVI, /RESTORE_BASE_SAVE_FILES
ENVI_BATCH_INIT, $
BATCH_LUN=batch_unit,$
LOG_FILE=sourceDir+'batch_log.txt'
[...]
BATCH_LUN correspond au numéro d’unité logique IDL de notre ficher log. Ce numéro
est nécessaire pour pouvoir écrire dans le fichier. Par exemple, si aucune image n’existe
dans notre répertoire d’entrée, on écrira:
[...]
imgFilepath = FILE_SEARCH(inputRep, '*.img', COUNT=nbFiles)
IF nbFiles EQ 0 THEN BEGIN
PRINTF, batch_unit, ’No files to process in this directory’
PRINTF, batch_unit, SYSTIME()
ENVI_BATCH_EXIT
RETURN
ENDIF
[...]
6
Tutoriel 2: lancer vos traitements en batch
De même si une erreur survient à l’ouverture de l’image d’entrée, il est nécessaire de
l’indiquer dans le fichier log:
[...]
ENVI_OPEN_FILE, imgFilepath[i], R_FID=fid
IF (fid EQ -1) THEN BEGIN
PRINTF, batch_unit, ’Could not open file ’+imgFilepath[i]
CONTINUE
ENDIF
[...]
Enfin, nous pouvons indiquer à la fin du programme que le traitement batch est terminé:
[...]
PRINTF, batch_unit, 'Batch process ended at '+SYSTIME()
ENVI_BATCH_EXIT
END
Ajout de nouveaux traitements
Nous allons montrer dans cette section combien il est facile d’adapter notre routine pour
effectuer de nouveaux traitements. Nous allons remplacer l’instruction chargée
d’appliquer un filtre de SOBEL, par l’enchainement d’une classification et d’un posttraitement: un filtrage majoritaire chargé d’éliminer les classes trop petites.
Pour ce faire, nous allons utiliser les routines suivantes: ENVI_DOIT, ’CLASS_DOIT’ et
ENVI_DOIT, `CLASS_MAJORITY_DOIT':
[...]
ENVI_DOIT, 'MATH_DOIT', EXP='SOBEL(b1)', $
FID=[fid], DIMS=dims, POS=[0], $
OUT_NAME=outputRep+$
FILE_BASENAME(imgFilepath[i], '.img') + '_sobel.img'
;; Classification non supervisee K-Means
class_names = ['unclass', 'cl1', 'cl2', 'cl3', 'cl4', 'cl5']
lookup = [[0,0,0],$
[255,0,0],[0,255,0],[0,0,255],[255,255,0],[0,255,255]]
ENVI_DOIT, 'CLASS_DOIT', FID=fid, DIMS=dims, POS=LINDGEN(nb), $
CLASS_NAMES=class_names, LOOKUP=lookup, METHOD=7,IN_MEMORY=0,$
ITERATION=1, CHANGE_THRESH=0.5, NUM_CLASSES=5, $
R_FID=r_fid, OUT_NAME=outputRep+$
FILE_BASENAME(imgFilepath[i], '.img') + '_kmean.img'
;; Filtrage majoritaire
ENVI_FILE_QUERY,r_fid, NS=ns,NL=nl,NB=nb,NUM_CLASSES=num_classes,$
ENVI_DOIT, 'CLASS_MAJORITY_DOIT', $
FID=r_fid, POS=[0], DIMS=[-1L, 0, ns-1, 0, nl-1], $
METHOD=0, KERNEL_SIZE=[5,5], $
OUT_NAME=outputRep+$
FILE_BASENAME(imgFilepath[i], '.img') + '_maj.img', $
CLASS_PTR=LONARR(num_classes)+1
[...]
Tutoriel 2: lancer vos traitements en batch
Ci-dessous, figure le code complet de ce deuxième exemple:
batch_processes2 (batch_processes2.pro)
PRO batch_processes2, inputRep, outputRep
COMPILE_OPT idl2
;; Test repertoire de sortie (contiendra les images traitees)
stack = SCOPE_TRACEBACK(/STRUCTURE)
sourceDir = FILE_DIRNAME((stack[N_ELEMENTS(stack)-1]).filename,$
/MARK_DIRECTORY)
IF N_ELEMENTS(outputRep) EQ 0 || ~FILE_TEST(outputRep) $
THEN outputRep = sourceDir
;; Test repertoire de’entree (contient les images a traiter)
default = FILEPATH('', ROOT_DIR=!DIR,$
SUBDIRECTORY=['products','envi42','data'])
IF N_ELEMENTS(inputRep) EQ 0 || ~FILE_TEST(inputRep) $
THEN inputRep = default
;; Restaurer ENVI en mode batch
ENVI, /RESTORE_BASE_SAVE_FILES
ENVI_BATCH_INIT, BATCH_LUN=batch_unit,$
LOG_FILE=sourceDir+'batch_log.txt'
;; Rechercher tous les fichiers ENVI situes
;; dans le repertoire d'entree
imgFilepath = FILE_SEARCH(inputRep, '*.img', COUNT=nbFiles)
IF nbFiles EQ 0 THEN BEGIN
PRINTF, batch_unit, 'No files to process in this directory'
PRINTF, batch_unit, SYSTIME()
ENVI_BATCH_EXIT
RETURN
ENDIF
FOR i=0, nbFiles-1 DO BEGIN
;; Lire l'image et recuperer le FID
ENVI_OPEN_FILE, imgFilepath[i], R_FID=fid
IF (fid EQ -1) THEN BEGIN
PRINTF, batch_unit, 'Could not open file '+imgFilepath[i]
CONTINUE
ENDIF
;; Infos sur le fichier
ENVI_FILE_QUERY, fid, DIMS=dims, NL=nl, NS=ns, NB=nb
;; Appliquer un filtre de SOBEL sur la 1ere bande
;; Sauvegarder l'image filtree
;ENVI_DOIT, 'MATH_DOIT', EXP='SOBEL(b1)', FID=[fid],$
;DIMS=dims, POS=[0], OUT_NAME=outputRep+$
7
8
Tutoriel 2: lancer vos traitements en batch
;FILE_BASENAME(imgFilepath[i], '.img') + '_sobel.img'
;; Rajouter une classification non supervisee
class_names = ['unclass', 'cl1', 'cl2', 'cl3', 'cl4', 'cl5']
lookup = [[0,0,0], $
[255,0,0],[0,255,0],[0,0,255],[255,255,0],[0,255,255]]
ENVI_DOIT, 'CLASS_DOIT', FID=fid, DIMS=dims, POS=LINDGEN(nb), $
CLASS_NAMES=class_names, LOOKUP=lookup, METHOD=7, $
IN_MEMORY=0, ITERATION=1, CHANGE_THRESH=0.5,NUM_CLASSES=5,$
R_FID=r_fid, OUT_NAME=outputRep+$
FILE_BASENAME(imgFilepath[i], '.img') + '_kmean.img'
ENVI_FILE_QUERY, r_fid, $
NS=ns, NL=nl, NB=nb, NUM_CLASSES=num_classes
ENVI_DOIT, 'CLASS_MAJORITY_DOIT', $
FID=r_fid, POS= [0], DIMS=[-1L, 0, ns-1, 0, nl-1], $
METHOD=0, KERNEL_SIZE=[5,5], $
OUT_NAME=outputRep+$
FILE_BASENAME(imgFilepath[i], '.img') + '_maj.img', $
CLASS_PTR=LONARR(num_classes)+1
ENDFOR
;; Indiquer dans notre fichier log que le traitement
;; batch est termine
PRINTF, batch_unit, 'Batch process ended at '+SYSTIME()
;; Fermer le mode batch
ENVI_BATCH_EXIT
END

Documents pareils