|
Metode dan Algoritma | Face Recognition Menggunakan Algoritma Eigenface Part 7 - Contoh Program + Source Code . Anda bisa melakukan konsultasi tentang Face Recognition Menggunakan Algoritma Eigenface Part 7 - Contoh Program + Source Code melalui form di samping kanan !!!
Fase Pengakuan
Gambar 8 menunjukkan mengenali () fungsi, yang mengimplementasikan fase pengakuan program Eigenface. Ini baru saja tiga langkah. Dua dari mereka – memuat gambar wajah dan memproyeksikan mereka ke ruang bagian tersebut – sudah akrab.
Gambar 8. (Klik untuk tampilan lebih besar) ini mengakui () fungsi mengimplementasikan fase pengakuan program Eigenface. |
Seperti dijelaskan di atas, gambar wajah untuk pengujian pengakuan harus tercantum dalam sebuah file bernama test.txt, menggunakan format yang sama seperti di train.txt. Pada baris 8, panggilan untuk loadFaceImgArray () beban ini ke faceImgArr dan menyimpan kebenaran dasar untuk nomor ID pada personNumTruthMat orang. Langkah ini mirip dengan baris 6 dari belajar () fungsi, dalam Gambar 4 . Di sini, jumlah gambar wajah yang disimpan dalam variabel lokal, nTestFaces.
Kita juga perlu memuat nTrainFaces variabel global serta sebagian besar data pelatihan lainnya – nEigens, EigenVectArr, pAvgTrainImg, dan sebagainya. Para loadTrainingData fungsi (), pada Gambar 9 , apakah itu bagi kita. Sekali lagi, fungsi OpenCV ketekunan kita membuat langkah ini mudah. Untuk membuka penyimpanan file untuk membaca, menggunakan bendera CV_STORAGE_READ. Kemudian, hanya panggilan Baca yang sesuai () fungsi untuk setiap variabel. OpenCV dan beban menempatkan setiap nilai data dalam file XML dengan nama.Ketika variabel adalah jenis CvMat, OpenCV menciptakan sebuah matriks baru untuk Anda secara otomatis, kemudian menetapkan nilai data.
Gambar 9. (Klik untuk tampilan lebih besar) fungsi OpenCV ketekunan kita membuatnya mudah untuk memuat data pelatihan disimpan dari file XML. |
Parameter terakhir di Baca () antarmuka fungsi adalah nilai default. Jika sebuah variabel bernama yang hilang dari file XML, maka akan diatur ke default. Untuk jenis pointer, seperti matriks, itu ide yang baik untuk mengatur default ke 0. Anda kemudian dapat menambahkan validasi cek untuk memastikan pointer ini memiliki nilai bukan nol sebelum Anda menggunakannya. Untuk menyederhanakan kode contoh, saya telah menghilangkan ini, dan langkah-langkah validasi serupa, dari loadTrainingData () fungsi.
Setelah semua data yang dimuat, langkah terakhir dalam fase pengakuan adalah proyek uji setiap gambar ke subruang PCA dan menemukan gambar yang diproyeksikan pelatihan terdekat. Untuk loop, pada baris 16-34 dari mengenali () fungsi ( Gambar 8 ), menerapkan langkah terakhir ini. Panggilan untuk cvEigenDecomposite (), yang proyek gambar tes, adalah mirip dengan kode wajah-proyeksi dalam belajar () fungsi.
Seperti sebelumnya, kita menyebarkannya jumlah nilai eigen (nEigens), dan array vektor eigen (eigenVectArr). Kali ini, bagaimanapun, kami melewati tes gambar, bukan gambar pelatihan, sebagai parameter pertama. Output dari cvEigenDecomposite () disimpan dalam variabel lokal – projectedTestFace. Karena tidak perlu untuk menyimpan gambar yang diproyeksikan tes, saya telah menggunakan array C untuk projectedTestFace, daripada matriks OpenCV.
Menemukan tetangga terdekat
Seperti artikel bulan lalu menjelaskan, eigenface “mengakui” citra wajah dengan mencari gambar pelatihan yang terdekat untuk itu dalam subruang PCA. Menemukan contoh pelatihan terdekat dalam subruang pelajari adalah teknik AI yang sangat umum. Ini disebut pencocokan Tetangga terdekat.
Gambar 10 menunjukkan kode untuk findNearestNeighbor () fungsi. Ini menghitung jarak dari tes gambar diproyeksikan untuk setiap contoh pelatihan diproyeksikan. Dasar jarak di sini adalah “Jarak Euclidean Squared.” Sebagai kolom bulan lalu menjelaskan, untuk menghitung jarak Euclidean antara dua titik, Anda akan menambahkan jarak kuadrat dalam dimensi masing-masing, kemudian mengambil akar kuadrat dari jumlah itu. Di sini, kita mengambil jumlah, tetapi melewatkan langkah akar kuadrat. Hasil akhir adalah sama, karena tetangga dengan jarak terkecil juga memiliki jarak kuadrat terkecil, sehingga kita dapat menghemat waktu perhitungan dengan membandingkan nilai kuadrat.
Gambar 10. (Klik untuk tampilan lebih besar) Para findNearestNeighbor () fungsi menghitung jarak dari tes gambar diproyeksikan untuk setiap contoh pelatihan diproyeksikan untuk mencari gambar pelatihan terdekat. |
Untuk loop pada baris 6-22 menghitung jarak kuadrat untuk setiap gambar yang diproyeksikan pelatihan, dan melacak (pada baris 18-21) yang citra pelatihan terdekat.
Nilai kembali adalah indeks dari gambar pelatihan terdekat. Dalam mengenali () fungsi ( Gambar 8 ), nilai ini kembali digunakan, pada baris 31, untuk mencari orang nomor ID yang terkait dengan citra pelatihan terdekat.
Berikut adalah output cetak dari mengenali () fungsi:
terdekat = 1, Kebenaran = 1
terdekat = 2, Kebenaran = 2
terdekat = 4, Kebenaran = 4
terdekat = 1, Kebenaran = 1
terdekat = 2, Kebenaran = 2
terdekat = 4, Kebenaran = 4
terdekat = 1, Kebenaran = 1
terdekat = 2, Kebenaran = 2
terdekat = 4, Kebenaran = 4
terdekat = 1, Kebenaran = 1
terdekat = 2, Kebenaran = 2
terdekat = 4, Kebenaran = 4
terdekat = 1, Kebenaran = 1
terdekat = 2, Kebenaran = 2
terdekat = 4, Kebenaran = 4
terdekat = 1, Kebenaran = 1
terdekat = 2, Kebenaran = 2
terdekat = 1, Kebenaran = 4
Tidak buruk! Kami hanya memiliki satu ketidaksesuaian: citra tes terakhir adalah misrecognized sebagai Subjek 1 bukan 4.
Meningkatkan Eigenface
Memiliki kerangka seperti ini untuk pelatihan dan pengujian akan membuat lebih mudah bagi Anda untuk menambahkan perbaikan Eigenface dan untuk menguji efek mereka.
Salah satu perbaikan pertama Anda mungkin ingin menambahkan adalah untuk mengubah cara jarak diukur. Kertas eigenface asli yang digunakan jarak Euclidean antara titik, dan itulah dasar jarak yang saya gunakan dalam findNearestNeighbors (). Tapi dasar yang berbeda, yang disebut jarak Mahalanobis (setelah penemunya) biasanya memberikan hasil yang lebih baik.
Salah satu hal yang terjadi ketika Anda memproyeksikan citra wajah ke subruang PCA adalah dimensi masing-masing menerima sejumlah peregangan. Jumlah peregangan tidak sama, meskipun, dalam setiap arah. Arah yang sesuai dengan nilai eigen terbesar mendapatkan membentang jauh lebih banyak daripada petunjuk terkait dengan nilai eigen lebih kecil. Karena jarak Euclidean mengabaikan peregangan ini, menggunakannya untuk mengukur jarak kira-kira sama dengan menggunakan hanya satu vektor eigen dan mengabaikan sisanya!
Sangat mudah untuk beralih dari Euclidean untuk jarak Mahalanobis. Hanya ubah baris 15, di findNearestNeighbors (), dari
distSq + = d_i * d_i;
untuk
distSq + = d_i * d_i/eigenValMat-> data.fl [i];
Beralih ke jarak Mahalanobis menghilangkan kesalahan ketidakcocokan yang disebutkan di atas, membawa akurasi pengenalan sampai dengan 100% untuk ketiga mata pelajaran.
Dimana untuk Go From Here?
Artikel ini memperkenalkan beberapa konsep baru OpenCV. Anda dapat memperoleh pemahaman yang lebih dalam dari ini dari dokumentasi OpenCV. Fungsi ketekunan, para CvTermCriteria struct, dan datatype CvMat dijelaskan secara rinci dalam dalam dokumentasi CXCORE. Fungsi eigenface dijelaskan dalam dokumentasi CVAUX. Dokumentasi CVAUX tidak terhubung dari halaman indeks dokumentasi, tapi Anda dapat menemukannya di dokumentasi ref subdirektori bernama. Saya juga membuat halaman di sini dengan link ke semuadokumentasi untuk OpenCV, versi 1.0.
Jika Anda ingin memasukkan Eigenface menjadi sistem yang dapat mendeteksi wajah dalam video langsung, Anda akan perlu untuk mendeteksi wajah, kemudian ekstrak ke gambar yang terpisah. Karena setiap gambar wajah harus persis ukuran yang sama, cara termudah untuk melakukannya adalah untuk menentukan ukuran standar, misalnya 50×50 pixel, depan waktu.Kemudian, ketika Anda mendeteksi wajah, anda dapat menggunakan kode seperti ini untuk mengekstrak dan mengubah ukurannya:
CvRect * pFaceRect = (CvRect *) cvGetSeqElem (pRectSeq, 0);
cvSetImageROI (pImg, * pFaceRect);
IplImage * pFaceImg =
cvCreateImage (STD_SIZE, IPL_DEPTH_8U, 1);
cvResize (pImg, pFaceImg, CV_INTER_AREA);
Ada kemampuan lebih dibangun ke OpenCV, dan banyak, lebih banyak program visi komputer satu dapat membuat menggunakan perpustakaan ini. Saya berharap seri artikel singkat telah memberi Anda rasa apa yang mungkin dengan OpenCV, dan mungkin memotivasi Anda untuk mengeksplorasi lebih dari kemampuannya.
Source Code :
AstarDemoApplet.java
[sourcecode language="java"]
// AstarDemoApplet.java by Robin Hewit, 2005
// Demonstrates A* search
import java.applet.*;
import java.awt.*;
import java.util.*;
public class AstarDemoApplet extends Applet {
static final String startSqString =
"Click on an open square to select the start.";
static final String startSqString2 =
"Start square = ";
static final String goalSqString =
"Click on an open square to select the goal.";
static final String goalSqString2 =
"Goal square = ";
static final String turnIsOffString =
"Turn penalty is OFF";
static final String turnIsOnString =
"Turn penalty is ON";
int nX = 13; // number of horizontal squares
int nY = 12; // number of vertical squares
// The grid map. Open squares are set to 1, closed squares to 0.
byte[][] map = new byte[nX][nY];
// GUI components. The GridMapView displays the grid map. It’s defined
// as an inner class for the applet. The labels give information about
// the applet’s state. The resetBtn clears the map. The goBtn executes
// a search.
GridMapView mapView;
Label clickStartLabel, clickGoalLabel, turnStateLabel;
Button resetBtn, goBtn;
Toggle turnToggle;
// State flags for whether the start and goal squares have been
// selected. The selected squares are stored in startSq and goalSq.
boolean startSqSet = false;
boolean goalSqSet = false;
MapSq startSq, goalSq;
// The class that implements A* Search on a grid map
AstarGridSearcher searcher;
///////////////////////////////////
// Inner class, MapSq
//
// Displays one grid-map square.
//
class MapSq extends Canvas {
public static final int L = 15;
int x, y;
Dimension dim;
// Constructor
MapSq(int x, int y) {
setBackground(Color.white);
dim = new Dimension(L, L);
this.x = x; this.y = y;
}
// The paint method outlines the map square in black
public void paint(Graphics g) {
g.setColor(Color.black);
g.drawLine(0,0, L-1, 0);
g.drawLine(0,0, 0,L-1);
g.drawLine(0,L-1, 0, 0);
g.drawLine(L-1, 0, 0, 0);
}
public int getX() { return x; }
public int getY() { return y; }
public Dimension preferredSize()
{ return dim; }
}
///////////////////////////////////
// Inner class, GridMapView
//
// Displays the grid map.
//
class GridMapView extends Panel {
int nX , nY;
MapSq[][] mapSq;
Dimension dim;
byte[][] map;
// Constructor
GridMapView(byte[][] map, int nX, int nY) {
dim = new Dimension(1+nX*(1+MapSq.L), 1+nY*(1+MapSq.L));
GridBagLayout gridbag = new GridBagLayout();
GridBagConstraints constraints = new GridBagConstraints();
setLayout(gridbag);
// save the map data
this.nX = nX;
this.nY = nY;
this.map = map;
mapSq = new MapSq[nX][nY];
// create the map squares and add them to the map
constraints.gridy = 1;
for(int y=0; y<nY; y++) {
constraints.gridx = 1;
for(int x=0; x<nX; x++) {
mapSq[x][y] = new MapSq(x,y);
add(mapSq[x][y]);
gridbag.setConstraints(mapSq[x][y], constraints);
constraints.gridx += 2+MapSq.L;
if(0 == map[x][y])
mapSq[x][y].setBackground(Color.black);
}
constraints.gridy += 2+MapSq.L;
}
}
// Sets a map square’s background color.
public void colorSq(int x, int y, Color c) {
try {
MapSq sq = (MapSq)getComponent(x + y*nX);
if(sq != null)
sq.setBackground(c);
} catch(Exception e) {}
}
// Restore the map view to its original state.
public void reset() {
for(int y=0; y<nY; y++)
for(int x=0; x<nX; x++)
if(0 == map[x][y])
colorSq(x,y,Color.black);
else
colorSq(x,y,Color.white);
}
public Dimension preferredSize()
{ return dim; }
}
///////////////////////////////////
// Inner class, Toggle
//
// Pop-up button that toggles a state variable.
//
class Toggle extends Canvas {
public boolean stateVar = false;
public String text = new String(" [toggle] ");
int textY;
boolean hovering = false;
boolean mouseDown = false;
Dimension dim = new Dimension();
// Constructor
public Toggle(FontMetrics fm) {
dim.height = 4+fm.getHeight();
dim.width = 4+fm.stringWidth(text);
textY = 3 + dim.height/2;
}
// paint() displays the button state and draws its text
public void paint(Graphics g) {
g.setColor(getBackground());
if(hovering)
g.fill3DRect(0, 0, dim.width-1, dim.height-1, true);
else if(mouseDown)
g.fill3DRect(0, 0, dim.width-1, dim.height-1, false);
else
g.fillRect(0, 0, dim.width-1, dim.height-1);
g.setColor(getForeground());
g.drawString(text, 1, textY);
}
// handleEvent() turns mouse clicks into Action events and sets state
public boolean handleEvent(Event evt) {
if(evt.id == Event.MOUSE_DOWN) {
stateVar = !stateVar;
evt.id = Event.ACTION_EVENT;
hovering = false;
mouseDown = true;
paint(getGraphics());
return super.handleEvent(evt);
} else if(evt.id == Event.MOUSE_UP) {
hovering = true;
mouseDown = false;
} else if(evt.id == Event.MOUSE_ENTER) {
hovering = true;
} else if(evt.id == Event.MOUSE_EXIT) {
hovering = false;
}
paint(getGraphics());
return true;
}
public Dimension preferredSize()
{ return dim; }
}
///////////////////////////////////
// init(), initializes the applet
//
// Lays out the GUI, creates the map, and
// instantiates the searcher.
//
public void init() {
createMap();
setLayout(null);
setBackground(Color.lightGray);
Dimension d;
FontMetrics fm = getGraphics().getFontMetrics();
int left = 10;
int top = 5;
// the GridMapView object
mapView = new GridMapView(map, nX, nY);
mapView.setBackground(Color.lightGray);
add(mapView);
d = mapView.preferredSize();
mapView.reshape(left, top, d.width, d.height);
// information text for the start square
top += d.height + 1;
clickStartLabel = new Label(startSqString, Label.LEFT);
clickStartLabel.setBackground(Color.yellow);
d = new Dimension();
d.width = 6+fm.stringWidth(startSqString);
d.height = 4+fm.getHeight();
add(clickStartLabel);
clickStartLabel.reshape(left, top, d.width, d.height);
// information text for the goal square
top += d.height + 1;
clickGoalLabel = new Label(goalSqString, Label.LEFT);
clickGoalLabel.setBackground(Color.lightGray);
add(clickGoalLabel);
clickGoalLabel.reshape(left, top, d.width, d.height);
// the "Reset Map" button to clear the map
top += d.height + 3;
d.height += 1;
resetBtn = new Button("Reset Map");
add(resetBtn);
d.width = 6+fm.stringWidth(new String("Reset Map"));
resetBtn.reshape(left, top, d.width, d.height);
resetBtn.disable();
// the "Find Path" button to do the search
goBtn = new Button("Find Path");
add(goBtn);
d.width = 6+fm.stringWidth(new String("Find Path"));
left += resetBtn.size().width + 5;
goBtn.reshape(left, top, d.width, d.height);
goBtn.disable();
// the turnStateLabel shows whether or not a turn penaly is selected
top += d.height + 7;
left -= resetBtn.size().width + 5;
turnStateLabel = new Label(turnIsOffString, Label.LEFT);
turnStateLabel.setBackground(Color.lightGray);
add(turnStateLabel);
d.width = 6+fm.stringWidth(turnIsOffString);
d.height -= 1;
turnStateLabel.reshape(left, top, d.width, d.height);
// turnStateToggle
left += turnStateLabel.size().width;
turnToggle = new Toggle(fm);
turnToggle.setBackground(Color.lightGray);
turnToggle.setForeground(Color.blue);
add(turnToggle);
d = turnToggle.preferredSize();
turnToggle.reshape(left, top, d.width, d.height);
// the AstarGridSearcher object
searcher = new AstarGridSearcher(map, nX, nY);
}
///////////////////////////////////
// paint()
//
// Updates the GUI. The label colors indicate the applet’s state.
// When the map is first reset, the start-square text is highlighted.
// After a start square’s been selected, the goal-square text is
// highlighted until a goal square’s selected.
//
public void paint(Graphics g) {
if(!startSqSet)
{
clickStartLabel.setBackground(Color.yellow);
clickGoalLabel.setBackground(Color.lightGray);
clickGoalLabel.setForeground(Color.lightGray);
} else if(!goalSqSet) {
clickStartLabel.setBackground(Color.lightGray);
clickGoalLabel.setBackground(Color.yellow);
clickGoalLabel.setForeground(Color.black);
} else {
clickStartLabel.setBackground(Color.lightGray);
clickGoalLabel.setBackground(Color.lightGray);
}
}
///////////////////////////////////
// handleEvent()
//
// Responds to applet events such as clicking a square
// or pressing a button.
//
public boolean handleEvent(Event evt) {
if(evt.id == Event.ACTION_EVENT) {
if(evt.target == resetBtn) {
// The "Reset Map" button was clicked
mapView.reset();
clickStartLabel.setText(startSqString);
clickGoalLabel.setText(goalSqString);
startSqSet = goalSqSet = false;
resetBtn.disable();
goBtn.disable();
} else if(evt.target == goBtn) {
// The "Find Path" button was clicked
Vector path = searcher.search
( new GridSquare(startSq.getX(), startSq.getY()),
new GridSquare(goalSq.getX(), goalSq.getY()),
turnToggle.stateVar );
// Show the path in red
mapView.reset();
for(int i=0; i<path.size(); i++) {
GridSquare sq = (GridSquare)path.get(i);
mapView.colorSq(sq.getX(), sq.getY(), Color.red);
}
} else if(evt.target == turnToggle) {
if(turnToggle.stateVar)
turnStateLabel.setText(turnIsOnString);
else
turnStateLabel.setText(turnIsOffString);
}
paint(getGraphics());
return true;
} else if(evt.id == Event.MOUSE_DOWN && evt.target instanceof MapSq) {
// A valid map square was selected
MapSq sq = (MapSq)evt.target;
int x = sq.getX();
int y = sq.getY();
if( (!startSqSet || !goalSqSet) && (map[x][y] != 0) ) {
sq.setBackground(Color.yellow);
if(!startSqSet) {
// It’s the start square
startSq = sq;
clickStartLabel.setText
(startSqString2 + "(" + x + ", " + y + ")");
startSqSet = true;
resetBtn.enable();
} else {
// It’s the goal square
goalSq = sq;
clickGoalLabel.setText
(goalSqString2 + "(" + x + ", " + y + ")");
goalSqSet = true;
goBtn.enable();
}
paint(getGraphics());
return true;
}
} else if(evt.id == Event.MOUSE_DOWN && evt.target == turnStateLabel) {
System.out.println("toggle");
}
return super.handleEvent(evt);
}
///////////////////////////////////
// createMap()
//
// Lays out the grid map pattern
//
void createMap() {
for(int y=0; y<nY; y++)
for(int x=0; x<nX; x++)
if(0==x || 0==y || nX-1 == x || nY-1 == y)
map[x][y] = 0; // border squares are blocked
else
map[x][y] = 1; // interior squares are initially all open
// now add some obstacles
map[2][3] = map[3][3] = map[4][3] = map[2][4] = map[3][4] = map[4][4]
= map[3][5] = map[4][5] = 0;
map[8][2] = map[9][2] = map[10][2] = 0;
for(int y=3; y<9; y++)
map[6][y] = map[7][y] = 0;
map[9][4] = map[9][5] = map[10][6] = map[10][7] = 0;
map[2][8] = map[3][8] = 0;
}
}
[/sourcecode]
AstarGridSearcher.java
[sourcecode language="java"]
// AstarGridSearcher.java by Robin Hewit, 2005
import java.util.Vector;
///////////////////////////////////
// AstarGridSearcher class
//
// Implements A* search on a grid map. Its search() method
// returns the path as a Vector of GridSquare objects.
//
public class AstarGridSearcher {
byte[][] map;
byte[][] flagMap;
int nX, nY;
Vector fringe = new Vector();
boolean addTurnPenalty = false;
GridSquare start, goal;
FringeNode endNode;
///////////////////////////////////
// Constructor
//
public AstarGridSearcher(byte[][] map, int nX, int nY) {
this.map = map;
this.nX = nX;
this.nY = nY;
flagMap = new byte[nX][nY];
}
///////////////////////////////////
// search(), the public search method
//
public Vector search
(GridSquare start, GridSquare goal, boolean addTurnPenalty) {
Vector path = new Vector();
fringe.removeAllElements();
this.start = start;
this.goal = goal;
this.addTurnPenalty = addTurnPenalty;
// reset the flag map
for(int y=0; y<nY; y++)
for(int x=0; x<nX; x++)
flagMap[x][y] = map[x][y];
// search
fringe.add( new FringeNode(null, start, goal, addTurnPenalty) );
if( findPath() ) {
FringeNode node = endNode;
while( null != node ) {
path.insertElementAt(node, 0);
node = node.parent;
}
}
return path;
}
///////////////////////////////////
// findPath()
//
// Recursive function that looks at the first
// node on the fringe.
//
boolean findPath() {
if( fringe.isEmpty() ) {return false;}
FringeNode node = (FringeNode)fringe.remove(0);
if( isGoal(node) ) {
endNode = node;
return true;
}
//if node isn’t closed, add its children to the fringe
if( 0 != flagMap[node.getX()][node.getY()] ) {
flagMap[node.getX()][node.getY()] = 0;
addChildrenToFringe(node);
}
return findPath();
}
///////////////////////////////////
// addChildrenToFringe()
//
void addChildrenToFringe(FringeNode parent) {
int x = parent.getX();
int y = parent.getY();
for(int dx=-1; dx<=1; dx++)
for(int dy=-1; dy<=1; dy++) {
int childX = x+dx;
int childY = y+dy;
if( 0 != flagMap[childX][childY] && 0 != map[childX][childY] )
if( diagonalIsClear(parent, dx, dy)) {
GridSquare sq = new GridSquare(childX, childY);
addToFringe(new FringeNode(parent,sq,goal,addTurnPenalty));
}
}
}
///////////////////////////////////
// diagonalIsClear()
//
// When moving along a diagonal, verify that adjacent squares
// to the sides are clear. Otherwise the robot might partially
// enter an obstructed square. This is not allowed.
//
boolean diagonalIsClear(FringeNode parent, int dx, int dy)
{
if(0==dy || 0==dx)
return true; // move isn’t along a diagonal
if( 0 == map[parent.getX()-1][parent.getY()] )
if( -1 == dx )
return false;
if( 0 == map[parent.getX()+1][parent.getY()] )
if( 1 == dx )
return false;
if( 0 == map[parent.getX()][parent.getY()-1] )
if( -1 == dy )
return false;
if( 0 == map[parent.getX()][parent.getY()+1] )
if( 1 == dy )
return false;
return true;
}
///////////////////////////////////
// addToFringe()
//
// Adds one node to the fringe, keeping the fringe
// ordered by actPlusL2Dist.
//
void addToFringe(FringeNode node) {
if( fringe.isEmpty() ) {
fringe.add(node);
} else {
double f = node.actPlusL2Dist;
for(int i=0; i<fringe.size(); i++) {
if( f < ((FringeNode)fringe.get(i)).actPlusL2Dist ) {
fringe.insertElementAt(node, i);
return;
}
}
fringe.insertElementAt(node, fringe.size());
}
}
///////////////////////////////////
// isGoal(), checks to see if a node is the goal
//
boolean isGoal(FringeNode node)
{ return (node.getX() == goal.getX() && node.getY() == goal.getY()); }
}
///////////////////////////////////
// FringeNode class
//
class FringeNode extends GridSquare {
public FringeNode parent;
public double actDist;
public double actPlusL2Dist;
///////////////////////////////////
// Constructor
//
public FringeNode
(FringeNode parent, GridSquare sq, GridSquare goal, boolean addTurnPenalty){
super(sq.x, sq.y);
this.parent = parent;
if(parent != null)
{
actDist = parent.actDist + computeDist(this, parent);
if(addTurnPenalty && null != parent.parent)
{
// if the path has changed directions, add a 0.5 turn penalty
FringeNode grandparent = parent.parent;
int dx1 = grandparent.getX() – parent.getX();
int dx2 = parent.getX() – this.getX();
if(dx1 != dx2)
actDist += 0.5;
else {
int dy1 = grandparent.getY() – parent.getY();
int dy2 = parent.getY() – this.getY();
if(dy1 != dy2) actDist += 0.5;
}
}
}
else
actDist = 0;
actPlusL2Dist = actDist + computeDist(this, goal);
}
///////////////////////////////////
// computeDist()
//
// computes the linear distance between two grid-map squares
//
static double computeDist(GridSquare node1, GridSquare node2) {
double dx = node1.getX() – node2.getX();
double dy = node1.getY() – node2.getY();
return Math.sqrt(dx*dx + dy*dy);
}
}
[/sourcecode]
GridSquare.java
[sourcecode language="java"]
// GridSquare.java by Robin Hewit, 2005
// Represents one square on a grid map
public class GridSquare {
int x, y;
public GridSquare(int x, int y) {
this.x = x;
this.y = y;
}
public int getX() { return x; }
public int getY() { return y; }
}
[/sourcecode]
CONTOH SOURCE CODE
Kode ini dapat digunakan / ditambahkan dalam aplikasi apapun dengan hanya menambahkan kelas yang ada ke dalam kode sumber Anda. Proses lainnya telah diimplementasikan dalam format yang mudah untuk dimengerti dan tepat sesuai dengan fleksibilitas program yang anda butuhkan.
Download Contoh Program + Source Code Artikel di Atas
Artikel lainnya :
+ Source Code ASP.NET + Source Code C++ + Source Code C-Sharp + Source Code Delphi + Source Code Java + Source Code JavaScript + Source code MATLAB + Source Code Ruby + Source Code VB.6.0 + Source Code VB.Net - Adaptive Resonance Theory (ART) - Algoritma & Pemrograman - Algoritma Backpropagation - Algoritma Blowfish - Algoritma Cipher - Algoritma Clustering Gaussians - Algoritma Eigenface - Algoritma Fuzzy C-Means - Algoritma Genetika - Algoritma Huffman - Algoritma Komputer Quantum - Algoritma LOKI - Algoritma MD5 - Algoritma Persamaan Diophantine - Algoritma Rijndael - Algoritma Semut - Algoritma Tabu Search - Analisis Kriteria Majemuk - Analytical Hierarchy Sistem (AHP) - Ant Colony System - Case Based Reasoning (CBR) - Chaotic Encryption Algorithm - Data Encryption Standard (DES) - Discrete Wavelet Transform - Elliptic Curve Digital Signature Algorithm (ECDSA) - Haar Wavelet - Hidden Markov Model (HMM) - JST Hopfield - Least Significant Bit (LSB) - Metode Analisis Heuristik - Metode Analisis Regresi - Metode Burrows-Wheeler Transform - Metode Forward Chaining - Metode Gost - Metode Huffman Statis - Metode Hybrid - Metode Insertion Heuristic - Metode Maksimum Likelihood - Metode Newton- Raphson - Metode Otsu - Metode Penyetaraan Histogram - Optical Character Recognition (OCR) - Propagasi Balik - Self Organizing Map (SOM) - Tabu Search - Teorema Bayes - Transformasi Wavelet Kontinyu Uncategorized ~ Artificial Intelligence ~ Blind Signature ~ Data Mining ~ Decission Support Sistem ~ Digital Signal Processing (DSP) ~ Digital Signature ~ Enkripsi & Dekripsi ~ Image & Data Prossesing ~ Jaringan MANET ~ Jaringan Neural Quantum ~ Jaringan Syaraf Tiruan ~ Judul Skripsi Tesis Informatika ~ Kecerdasan Buatan ~ Kriptografi ~ Model Pemrograman Linear (MPL) ~ Multiple Trip Vehicle Routing Problem (MTVRP) ~ Neural Network ~ Pengenalan Pola ~ Pengenalan Wajah ~ Pengolahan Citra ~ Penjadwalan ~ Pewarnaan Simpul Graph ~ Recognition ~ Sistem Pakar ~ Steganography ~ Tanda Tangan Digital ~ Traveling Salesman Problem (TSP) ~ Watermarking
Face Recognition Menggunakan Algoritma Eigenface Part 7 - Contoh Program + Source Code
ActionScript AS3 ASP.NET AJAX C / C++ C# Clipper COBOL ColdFusion DataFlex Delphi Emacs Lisp Fortran FoxPro Java J2ME JavaScript JScript Lingo MATLAB Perl PHP PostScript Python SQL VBScript Visual Basic 6.0 Visual Basic .NET Flash MySQL Oracle Android
Rating: 100% based on 99998 ratings. 5 user reviews.
Ditulis Oleh hank2
{ 0 komentar... Views All / Send Comment! }
Posting Komentar