ΤΕΧΝΟΛΟΓΙΚΟ ΕΚΠΑΙΔΕΥΤΙΚΟ ΙΔΡΥΜΑ ΚΡΗΤΗΣ ΣΧΟΛΗ ΤΕΧΝΟΛΟΓΙΚΩΝ ΕΦΑΡΜΟΓΩΝ ΔΙΑΤΜΗΜΑΤΙΚΟ ΠΡΟΓΡΑΜΜΑ ΜΕΤΑΠΤΥΧΙΑΚΩΝ ΣΠΟΥΔΩΝ ΠΡΟΗΓΜΕΝΑ ΣΥΣΤΗΜΑΤΑ ΠΑΡΑΓΩΓΗΣ ΑΥΤΟΜΑΤΙΣΜΟΥ & ΡΟΜΠΟΤΙΚΗΣ ΜΗΧΑΝΙΚΗ ΟΡΑΣΗ 1η ΕΡΓΑΣΙΑ ΣΠΟΥΔΑΣΤΕΣ: ΕΙΣΗΓΗΤΗΣ ΔΗΜΟΠΟΥΛΟΣ ΑΝΔΡΕΑΣ ΑΜ: ΜΗ62 ΔΡ ΜΑΚΡΗΣ ΑΛ. ΧΑΡΚΙΟΛΑΚΗΣ ΜΙΧΑΛΗΣ ΑΜ: ΜΗ69 ΧΕΙΜΕΡΙΝΟ ΕΞΑΜΗΝΟ 2016-2017
ΑΣΚΗΣΗ 1 Στην παρούσα εργασία ζητείται να παρουσιαστεί ένα ιστόγραμμα μέσω της συνάρτησης MyHist που θα αναπτυχθεί, που θα κατηγοριοποιεί την φωτεινότητα μιας εικόνας που θα δώσει ο χρήστης στα bins που θέλει ο χρήστης. Μέσω Matlab αυτό μπορεί να γίνει με την εντολή imhist που στην παρούσα άσκηση θα γίνει μόνο η επαλήθευση. Το script που αναπτύχθηκε είναι το παρακάτω: clear all ; clc; %γίνεται καθαρισμός του ιστορικού I=imread('cameraman.tif'); %διαβάζεται η εικόνα n=255; %Ο χρήστης δίνει τιμή bins H=myHist(I,n); %Εκτελείται η συνάρτηση myhist που θα %παρουσιαστεί παρακάτω I=im2uint8(I); %μετατρέπεται η εικόνα σε uint8 σε περίπτωση %που δεν είναι Isize=size(I); %Καταχωρούμε σε έναν πίνακα το μέγεθος της %εικόνας προκειμένου να ελέγξουμε εάν είναι %ασπρόμαυρη ή RGB εικόνα if (length(isize)==3) %Εάν η εικόνα έχει 3 επίπεδα είναι RGB I=rgb2gray(I); %οπότε την μετατρέπουμε % ανοίγουμε ένα νέο παράθυρο imshow(i) % προβάλουμε στον χρήστη την εικόνα που % αναλύσαμε % ανοίγουμε νέο παράθυρο imhist((i)) % επαληθεύουμε με την συνάρτηση imhist για % να δούμε εάν τα 2 γραφήματά μας μοιάζουν. Η συνάρτηση myhist που καλείται στο παραπάνω script είναι το παρακάτω: function [ H ] = myhist( I, n ) I=im2uint8(I); %μετατρέπεται η εικόνα σε uint8 σε περίπτωση %που δεν είναι Isize=size(I); % Καταχωρούμε σε έναν πίνακα το μέγεθος της %εικόνας προκειμένου να ελέγξουμε εάν είναι %ασπρόμαυρη ή RGB εικόνα if (length(isize)==3) %Εάν η εικόνα έχει 3 επίπεδα είναι RGB I=rgb2gray(I); %οπότε την μετατρέπουμε J=zeros(1,n); %δημιουργούμε ένα πίνακα με μηδενικά τόσα όσα %και τα bins που έδωσε ο χρήστης bima=(255/n); %κάνουμε την διαίρεση προκειμένου να βρούμε το %βήμα που θα κατηγοριοποιηθούν τα bims for i = 1:n; %αρχίζει μια διαδικασία ταξινόμησης D=bima*i; %είναι ουσιαστικά το ανώτερο όριο κάθε βήματος E=find(I>(D-bima) & I<=D); % Η εντολή αυτή εξηγείται παρακάτω Z=size(E,1); % καταχωρεί το μέγεθος του πίνακα σε μια % μεταβλητή H(i)=Z; % καταχωρεί τον αριθμό αυτόν σε κάθε στοιχείο % του πίνακα stem(h) ΔΗΜΟΠΟΥΛΟΣ ΑΝΔΡΕΑΣ ΧΑΡΚΙΟΛΑΚΗΣ ΜΙΧΑΛΗΣ 1
Η εντολή find που παρουσιάστηκε παραπάνω, με τον τρόπο που συντάχθηκε, ουσιαστικά ψάχνει για τιμές μέσα στον πίνακα της εικόνας που να ικανοποιούν τις δυο συνθήκες που του θέσαμε. Σε περίπτωση που ικανοποιούνται οι συνθήκες (I>(Dbima) & I<=D) τότε και μόνο τότε θέτει στην μεταβλητή Ε ένα νέο στοιχείο στον πίνακά της. Για παράδειγμα: Έστω ότι έχουμε τον παρακάτω πίνακα: X = [1 0 4-3 0 0 0 8 6]; Και γράψουμε i = find(x > 2) Αυτό θα μας επιστρέψει μόνο τις θέσεις των νούμερων του πίνακα Χ που η τιμή του είναι μεγαλύτερα του 2 και θα τα καταχωρήσει στον πίνακα i. Ο πίνακας i εν συνεχεία δημιουργεί τόσες κολόνες όσες και οι τιμές που ικανοποιούν την συνθήκη αυτή. Άρα στο συγκεκριμένο παράδειγμα θα μας δώσει έναν πίνακα 1X3 i = 3 8 9 Γίνεται αντιληπτό ότι στη συνέχεια ο πίνακας που θα έχει σχηματιστεί (ο Ε στην περίπτωση της άσκησής μας) μας ενδιαφέρει να μάθουμε το μέγεθός του και όχι και τα σημεία του πίνακα που εντοπίστηκαν τα νούμερα αυτά προκειμένου να δούμε πόσες φορές εμφανίζεται το συγκεκριμένο pixel στην εικόνα. Το παραπάνω script και function το σχεδιάσαμε με τέτοιο τρόπο ώστε να δέχεται κάθε μορφής εικόνα ακόμα και εάν είναι RGB. Το επαληθεύσαμε με διάφορες εικόνες μία εκ των οποίων είναι και η παρακάτω: ΔΗΜΟΠΟΥΛΟΣ ΑΝΔΡΕΑΣ ΧΑΡΚΙΟΛΑΚΗΣ ΜΙΧΑΛΗΣ 2
To ιστόγραμμα που μας εμφάνισε όταν τρέξαμε το script είναι: Η εικόνα: Και η επαλήθευση με την εντολή imhist ΔΗΜΟΠΟΥΛΟΣ ΑΝΔΡΕΑΣ ΧΑΡΚΙΟΛΑΚΗΣ ΜΙΧΑΛΗΣ 3
ΑΣΚΗΣΗ 2 Σε αυτήν την άσκηση ζητήθηκε να αναπτυχθεί ένας κώδικας μέσω του matlab όπου ο χρήστης θα δίνει μια εικόνα που θα είναι πολύ σκοτεινή ή φωτεινή και το matlab θα την επεξεργάζεται και θα την εμφανίζει με κανονική φωτεινότητα. Στις uint8 εικόνες, η ένταση της φωτεινότητας ταξινομείται από 1 έως 255. Όταν μια εικόνα είναι πολύ σκοτεινή, πολλά από τα pixel της εικόνας έχουν τιμές πολύ χαμηλές. Αντιθέτως στις πολύ φωτεινές εικόνες οι τιμές των pixels παίρνουν τιμές υψηλές με μέγιστο το 255. Για να κάνουμε την εικόνα να εμφανίζεται σε κανονική ένταση, μπορούμε να εξομαλύνουμε την κατανομή των pixels της εικόνας σε όλο το φάσμα της φωτεινότητας. Ουσιαστικά να κανονικοποιήσουμε το ιστόγραμμα της εικόνας. Συντάχθηκε το παρακάτω script: clear all ; clc; %γίνεται καθαρισμός του ιστορικού I=imread('44.jpg'); %διαβάζεται η εικόνα Isize=size(I); %Καταχωρούμε σε έναν πίνακα το μέγεθος της %εικόνας προκειμένου να ελέγξουμε εάν είναι %ασπρόμαυρη ή RGB εικόνα if (length(isize)==3) %Εάν η εικόνα έχει 3 επίπεδα είναι RGB I=rgb2gray(I); %οπότε την μετατρέπουμε In=myNormalize(I); %καλούμε την συνάρτηση mynormalize %ανοίγουμε ένα νέο παράθυρο imshow(i) %εμφανίζουμε την αρχική εικόνα title('αρχική εικόνα'); %δίνουμε τίτλο στο παράθυρο %εμφανίζουμε την επεξεργασμένη εικόνα imshow(in) title('επεξερασμένη εικόνα'); %εμφανίζουμε το ιστόγραμμα της αρχικής %εικόνας imhist((i)); title('ιστόγραμμα αρχικής εικόνας'); imhist((in)); %εμφανίζουμε το ιστόγραμμα της %επεξεργασμένης εικόνας title('ιστόγραμμα επεξεργασμένης εικόνας'); Όπου η συνάρτηση mynormilize είναι η παρακάτω: function [ In ] = mynormalize( I ) I=double(I); %μετατρέπουμε την εικόνα σε double επειδή σε %uint8 δεν μπορούμε να κάνουμε πράξεις picmin=min(min(i)); %βρίσκει την ελάχιστη τιμή της εικόνας picmax=max(max(i)); %βρίσκει την μέγιστη τιμή της εικόνας In=(I - picmin) * 255 / (picmax - picmin); %εφαρμόζουμε τον τύπο της %κανονικής κατανομής In=uint8(In); %την ξαναμετατρέπουμε σε uint8 αφού %ολοκληρώσαμε τις πράξεις μας. ΔΗΜΟΠΟΥΛΟΣ ΑΝΔΡΕΑΣ ΧΑΡΚΙΟΛΑΚΗΣ ΜΙΧΑΛΗΣ 4
Oι τιμές του πίνακά μας κανονικοποιήθηκαν με την μέθοδο της κανονικοποίησης ελάχιστου-μέγιστου. «Με αυτήν τη μέθοδο κανονικοποίησης, οι αριθμητικές τιμές αντιστοιχίζονται με άλλες, οι οποίες κυμαίνονται εντός μιας προκαθορισμένης περιοχής τιμών. Η αντιστοίχιση γίνεται με γραμμικό μετασχηματισμό. Αν θεωρήσουμε μια μεταβλητή Α, όπου η μεγαλύτερη τιμή της είναι η maxa και η μικρότερη τιμή της είναι η mina, μπορούμε να αντιστοιχίσουμε όλες τις τιμές με άλλες που κυμαίνονται εντός μιας περιοχής με κατώτερο όριο την new_mina και ανώτερο όριο την new_maxa σύμφωνα με τη Σχέση x = x min A max A min A (new_max A new_min A ) + new_min A όπου x η εκάστοτε τιμή της μεταβλητής Α και x η νέα τιμή. Η μέθοδος αυτή έχει το πλεονέκτημα ότι ο χρήστης προκαθορίζει την περιοχή τιμών, για παράδειγμα μπορεί να μετασχηματίσει τις τιμές έτσι ώστε να κυμαίνονται στην περιοχή [0,0..1,0], ορίζοντας σαν new_mina την τιμή 0 και σαν new_maxa την τιμή 1. Επίσης, με τη μέθοδο αυτή διατηρείται η αναλογία μεταξύ των τιμών που υπήρχε στα αρχικά δεδομένα.» απόσπασμα από : https://repository.kallipos.gr/bitstream/11419/1234/2/kef._7.pdf στην περίπτωση μας: x : η επεξεργασμένη εικόνα x : η αρχική εικόνα mina: η ελάχιστη τιμή της αρχικής εικόνας maxa: η μέγιστη τιμή της αρχικής εικόνας new_maxa : η τιμή 255 new_mina: η τιμή 0 συνεπώς ο παραπάνω τύπος έγινε για την περίπτωσή μας ο εξής x = x min A (255 0) + 0 = (x min A ) 255 max A min A max A min A Ο παραπάνω κώδικας έτρεξε για διάφορες εικόνες και τα αποτελέσματα που πήραμε ήταν τα εξής: ΔΗΜΟΠΟΥΛΟΣ ΑΝΔΡΕΑΣ ΧΑΡΚΙΟΛΑΚΗΣ ΜΙΧΑΛΗΣ 5
1 η εικόνα: 2 η εικόνα: ΔΗΜΟΠΟΥΛΟΣ ΑΝΔΡΕΑΣ ΧΑΡΚΙΟΛΑΚΗΣ ΜΙΧΑΛΗΣ 6
3 η εικόνα ΔΗΜΟΠΟΥΛΟΣ ΑΝΔΡΕΑΣ ΧΑΡΚΙΟΛΑΚΗΣ ΜΙΧΑΛΗΣ 7
ΑΣΚΗΣΗ 3 a) Στην παρούσα άσκηση ζητείται να γραφτεί μια συνάρτηση (function) όπου θα παίρνει ως είσοδο το εστιακό βάθος (focal length) f της κάμερας, το μέγεθος της εικόνας σε pixels (μήκος, ύψος) και έναν δείκτη P που αντιπροσωπεύει τα τρισδιάστατα σημεία του χώρου. Η συνάρτηση αυτή θα επιστρέφει τα σημεία που αντιπροσωπεύουν το σημείο αυτό στον δισδιάστατο κόσμο καθώς επίσης και μια λογική τιμή (0 ή 1) εάν το σημείο αυτό είναι εντός της εικόνας ή όχι. Συντάχθηκε το παρακάτω script: clear all; clc; f=20; %δίνουμε τιμή στο εστιακό βάθος im_size(1)=850; %Δηλώνουμε το μήκος της εικόνας im_size(2)=700; %Δηλώνουμε το ύψος της εικόνας P=[1000;1000;250]; %Δηλώνουμε το σημείο στον τρισδιάστατο %χώρο [p,valid]=myproject(f,im_size,p) %τρέχουμε την συνάρτηση Η συνάρτηση myproject είναι η παρακάτω: function [ p,valid] = myproject( f,im_size,p ) Uo=im_size(1); %καταχωρούμε στο Uo το μήκος της εικόνας Vo=im_size(2); %καταχωρούμε στο Vo το ύψος της εικόνας Pplus=[P;1]; %προσθέτουμε στον πίνακα P άλλη μια %γραμμή προκειμένου να μπορέσουμε να %κάνουμε πράξη μεταξύ των πινάκων F=[f,0,Uo/2, 0;0, f,vo/2,0;0,0,1, 0]; %φτιάχνουμε τον πίνακα pnew=f*pplus; %κάνουμε τον πολλαπλασιασμό των πινάκων w=pnew/pnew(3); %κάνουμε την διαίρεση του κάθε στοιχείου %με το w προκειμένου να πάρουμε τα u και v p=w(1:2,1); %καταχωρούμε σε έναν πίνακα τις 2 πρώτες %γραμμές που θέλουμε να εξάγουμε u=w(1); %καταχωρούμε σε μία μεταβλητή την τιμή %της πρώτης γραμμής του πίνακα %προκειμένου να κάνουμε έλεγχο v=w(2); %καταχωρούμε σε μία μεταβλητή την τιμή %της δεύτερης γραμμής του πίνακα %προκειμένου να κάνουμε έλεγχο valid=((u<=uo)&(v<=vo)); %ελέγχουμε αν είναι εντός της εικόνας το %σημείο αυτό ΔΗΜΟΠΟΥΛΟΣ ΑΝΔΡΕΑΣ ΧΑΡΚΙΟΛΑΚΗΣ ΜΙΧΑΛΗΣ 8
Ουσιαστικά στην παραπάνω function έγινε η παρακάτω πράξη: Όπου στον παραπάνω τύπο επιλέξαμε uo και vo τιμές μη μηδενικές και συγκεκριμένα τιμές ίσον με το μήκος δια δύο και το ύψος δια δύο της εικόνας προκειμένου να τοποθετήσουμε το οπτικό κέντρο στο κέντρο της εικόνας. Τρέξαμε την παραπάνω function με τις εξής τιμές: clear all; clc; f=20; im_size(1)=850; im_size(2)=700; P=[0;0;10]; [p,valid]=myproject(f,im_size,p) Και πήραμε το αποτέλεσμα: p = 425 350 valid = 1 Τρέξαμε την παραπάνω function με τις εξής τιμές: clear all; clc; f=50; im_size(1)=640; im_size(2)=480; P=[10;0;10]; [p,valid]=myproject(f,im_size,p) Και πήραμε το αποτέλεσμα: p = 370 240 valid = 1 Τρέξαμε την παραπάνω function με τις εξής τιμές: clear all; clc; f=1000; im_size(1)=640; im_size(2)=480; P=[10;10;20]; [p,valid]=myproject(f,im_size,p) ΔΗΜΟΠΟΥΛΟΣ ΑΝΔΡΕΑΣ ΧΑΡΚΙΟΛΑΚΗΣ ΜΙΧΑΛΗΣ 9
Και πήραμε το αποτέλεσμα: p = 820 740 valid = 0 b) Στο δεύτερο ερώτημα ζητείται να γίνει η ίδια διαδικασία με την διαφορά να μπορεί να λαμβάνει ως είσοδο η function περισσότερα σημεία προς έλεγχο και να τα μετατρέπει σε σημεία στον δισδιάστατο χώρο και να κάνει έλεγχο κάθε φορά αν τα σημεία αυτά είναι σημείο μέσα στα όρια της εικόνας ή όχι. Με βάση τα παραπάνω το script τώρα έγινε: clear all; clc; f=500; im_size(1)=640; im_size(2)=480; load('3dpoints_b.mat'); [p,valid]=myprojectm(f,im_size,p) %τρέχουμε το αρχείο με έναν πίνακα που %έχει πολλά σημεία προς έλεγχο και η myprojectm function μετατρέπεται ως: function [ p,valid] = myprojectm( f,im_size,p ) [a,b]=size(p); Uo=im_size(1); Vo=im_size(2); V=ones(1,b); %καταχωρούμε το μέγεθος του πίνακα P σε μία %μεταβλητή για να ξέρουμε πόσες επαναλήψεις θα κάνουμε %δημιουργούμε έναν πίνακα με άσσους τόσους όσες και %οι στήλες του πίνακα P Pplus=[P;V]; %προσαρτούμε τον πίνακα με τους άσσους στην τελευταία %σειρά του πίνακα P ώστε να γίνουν οι πράξεις for i=1:b %αρχίζει η επανάληψη της διαδικασίας για κάθε στήλη F=[f,0,Uo/2, 0;0, f,vo/2,0;0,0,1, 0]; pnew=f*pplus(:,i); w=pnew/pnew(3); p(:,i)=w(1:2,1); %καταχωρούμε σε έναν νέο πίνακα κάθε τιμή που %βρίσκουμε u=w(1); v=w(2); valid(:,i)=((u<=uo)&(v<=vo)); %το ίδιο κάνουμε και για τον πίνακα με %τα μηδενικά ή τους άσσους (είναι δεν %είναι σημείο της εικόνας ΔΗΜΟΠΟΥΛΟΣ ΑΝΔΡΕΑΣ ΧΑΡΚΙΟΛΑΚΗΣ ΜΙΧΑΛΗΣ 10