FaceDescriptor processImage(string path, string name, bool isPhoto) { Image <Bgr, byte> image = new Image <Bgr, byte>(path); Rectangle realFace; Rectangle[] realEyes; Rectangle realMouth; Rectangle[] faces; Rectangle[] eyes; Rectangle[] mouths;//placeholder for out, not important for query faceDetection.faceAndLandmarks(image, out realFace, out realEyes, out realMouth, out faces, out eyes, out mouths); if (realFace.Width == 0) { return(null); } var extendedFace = faceDetection.extendFace(image, realFace, faceDetection.faceOutline(image)); image = image.GetSubRect(extendedFace); FaceDescriptor face = new FaceDescriptor(name); realMouth.X += realFace.X - extendedFace.X; realMouth.Y += realFace.Y - extendedFace.Y; Point leftEye = new Point(); Point rightEye = new Point(); if (realEyes.Length == 2) { faceDetection.eyesCenter(realEyes, out leftEye, out rightEye); leftEye.X += realFace.X - extendedFace.X; leftEye.Y += realFace.Y - extendedFace.Y; rightEye.X += realFace.X - extendedFace.X; rightEye.Y += realFace.Y - extendedFace.Y; if (isPhoto) { Point rotatedLeftEye; Point rotatedRightEye; image = faceDetection.alignEyes(image, leftEye, rightEye, out rotatedLeftEye, out rotatedRightEye); leftEye = rotatedLeftEye; rightEye = rotatedRightEye; realMouth = faceDetection.getMouth( image.GetSubRect( new Rectangle(new Point(0, 0), new Size((int)(image.Width * 0.9), (int)(image.Height * 0.9))) )); } } Rectangle hair; Rectangle brow; Rectangle roiEyes; Rectangle nose; faceDetection.faceROI(image, leftEye, rightEye, realMouth, out hair, out brow, out roiEyes, out nose, out realMouth); Image <Bgr, byte> hairImage; Image <Bgr, byte> browImage; Image <Bgr, byte> eyesImage; Image <Bgr, byte> noseImage; Image <Bgr, byte> mouthImge; roiToFixedImage(image, hair, brow, roiEyes, nose, realMouth, out hairImage, out browImage, out eyesImage, out noseImage, out mouthImge); face.HairHog = hogDescriptor.GetHog(hairImage, 32, 16); face.BrowHog = hogDescriptor.GetHog(browImage, 32, 16); face.EyesHog = hogDescriptor.GetHog(eyesImage, 32, 16); face.NoseHog = hogDescriptor.GetHog(noseImage, 16, 8); face.MouthHog = hogDescriptor.GetHog(mouthImge, 16, 8); face.HairSift = siftDescriptor.ComputeDescriptor(hairImage, 24, 16); face.BrowSift = siftDescriptor.ComputeDescriptor(browImage, 24, 16); face.EyesSift = siftDescriptor.ComputeDescriptor(eyesImage, 24, 16); face.NoseSift = siftDescriptor.ComputeDescriptor(noseImage, 8, 12); face.MouthSift = siftDescriptor.ComputeDescriptor(mouthImge, 12, 8); face.processDescriptors(); return(face); }
// main query method public void search(String sketchPath, BackgroundWorker worker = null, bool progressOnlyDescriptor = false) { bool progress = (worker != null); if (sketchPath.Equals("")) { return; } if (lda == null) { lda = LDA.loadTraining( TRAINING_SIZE, TEST_SIZE, SKETCH_PATH, SKETCH_EXTENSION, LDA_FILE_NAME, out trainingSetSketchesPath, out testSetSketchesPath ); } if (descriptors == null) { if (File.Exists(DESCRIPTOR_FILE_NAME)) { Stream openFileStream = File.OpenRead(DESCRIPTOR_FILE_NAME); BinaryFormatter deserializer = new BinaryFormatter(); descriptors = (List <FaceDescriptor>)deserializer.Deserialize(openFileStream); openFileStream.Close(); } else { descriptors = new List <FaceDescriptor>(); List <FileInfo> files = new List <FileInfo>(); DirectoryInfo dinfo = new DirectoryInfo(PHOTO_PATH); files.AddRange(dinfo.GetFiles(PHOTO_EXTENSION)); dinfo = new DirectoryInfo(OTHER_PHOTO_PATH); files.AddRange(dinfo.GetFiles(PHOTO_EXTENSION)); files.AddRange(dinfo.GetFiles(OTHER_PHOTO_EXTENSION)); for (int i = 0; i < files.Count; i++) { FaceDescriptor face = processImage(files[i].FullName, files[i].Name, true); if (face != null) { descriptors.Add(face); } if (progress) { worker.ReportProgress(i * 100 / files.Count); } } Stream SaveFileStream = File.Create(DESCRIPTOR_FILE_NAME); BinaryFormatter serializer = new BinaryFormatter(); serializer.Serialize(SaveFileStream, descriptors); SaveFileStream.Close(); } LDA.training(lda, descriptors, trainingSetSketchesPath, processImage, TRAINING_SIZE, LDA_FILE_NAME, worker); for (int i = 0; i < descriptors.Count; i++) { for (int k = 0; k < descriptors[i].DescriptorHog.Count(); k++) { descriptors[i].DescriptorHog[k] *= (float)lda.projectingVectorHOG[k]; } for (int k = 0; k < descriptors[i].DescriptorSift.Count(); k++) { descriptors[i].DescriptorSift[k] *= (float)lda.projectingVectorSIFT[k]; } } } if (progress && !progressOnlyDescriptor) { worker.ReportProgress(0); } sketchName = sketchPath.Substring(sketchPath.LastIndexOf('\\') + 1, 5); FaceDescriptor sketchFace = processImage(sketchPath, sketchName, false); resultHog = new SortedDictionary <double, string>(); resultSift = new SortedDictionary <double, string>(); resultBordaCount = new SortedDictionary <double, string>(); for (int i = 0; i < sketchFace.DescriptorHog.Count(); i++) { sketchFace.DescriptorHog[i] *= (float)lda.projectingVectorHOG[i]; } for (int i = 0; i < sketchFace.DescriptorSift.Count(); i++) { sketchFace.DescriptorSift[i] *= (float)lda.projectingVectorSIFT[i]; } int hogSize = 540; int siftSize = 512; for (int i = 0; i < descriptors.Count; i++) { addDictionaryUnique( euclideanDistance( sketchFace.DescriptorHog, descriptors[i].DescriptorHog, hogSize ), descriptors[i].Name, resultHog); addDictionaryUnique( euclideanDistance( sketchFace.DescriptorSift, descriptors[i].DescriptorSift, siftSize ), descriptors[i].Name, resultSift); if (progress && !progressOnlyDescriptor) { worker.ReportProgress(i * 100 / descriptors.Count); } } Dictionary <string, int> dictionary = new Dictionary <string, int>(); int count = 0; foreach (var r in resultHog) { dictionary.Add(r.Value, (resultHog.Count - count) * 2);//weight count++; } count = 0; foreach (var r in resultSift) { dictionary[r.Value] += resultSift.Count - count; count++; } foreach (var r in dictionary) { double value = r.Value; //negative int because sorted dictionary work in ascending mode only addDictionaryUnique(-r.Value, r.Key, resultBordaCount); } if (progress && !progressOnlyDescriptor) { worker.ReportProgress(100); } }
public static void training( LDA lda, List <FaceDescriptor> descriptors, List <string> trainingSetSketchesPath, Func <string, string, bool, FaceDescriptor> processImage, int TRAINING_SIZE, string LDA_FILE_NAME, BackgroundWorker worker = null ) { bool progress = (worker != null); if (lda.projectingVectorHOG == null) { List <FaceDescriptor> trainingDescriptors = new List <FaceDescriptor>(); for (int i = 0; i < trainingSetSketchesPath.Count; i++) { FaceDescriptor face = processImage(trainingSetSketchesPath[i], lda.trainingSet[i], true); if (face != null) { trainingDescriptors.Add(face); } if (progress) { worker.ReportProgress(i * 100 / trainingSetSketchesPath.Count); } } if (progress) { worker.ReportProgress(0); } Dictionary <string, FaceDescriptor> descriptorsWithName = new Dictionary <string, FaceDescriptor>(); foreach (var descriptor in descriptors) { string name = descriptor.Name.Substring(0, 5); if (!descriptorsWithName.ContainsKey(name)) { descriptorsWithName.Add(name, descriptor); } } int NPoints = TRAINING_SIZE * 2; int NClasses = TRAINING_SIZE; int NVarsHOG = trainingDescriptors[0].DescriptorHog.Count(); int NVarsSIFT = trainingDescriptors[0].DescriptorSift.Count(); double[,] xyHOG = new double[NPoints, NVarsHOG + 1]; double[,] xySIFT = new double[NPoints, NVarsSIFT + 1]; for (int i = 0; i < TRAINING_SIZE; i++) { FaceDescriptor photoDescriptor = descriptorsWithName[trainingDescriptors[i].Name]; for (int k = 0; k < NVarsHOG; k++) { xyHOG[i, k] = trainingDescriptors[i].DescriptorHog[k]; xyHOG[i + TRAINING_SIZE, k] = photoDescriptor.DescriptorHog[k]; } xyHOG[i, NVarsHOG] = i; xyHOG[i + TRAINING_SIZE, NVarsHOG] = i; for (int k = 0; k < NVarsSIFT; k++) { xySIFT[i, k] = trainingDescriptors[i].DescriptorSift[k]; xySIFT[i + TRAINING_SIZE, k] = photoDescriptor.DescriptorSift[k]; } xySIFT[i, NVarsSIFT] = i; xySIFT[i + TRAINING_SIZE, NVarsSIFT] = i; if (progress) { worker.ReportProgress(i * 100 / TRAINING_SIZE); } } int info = 0; double[] wHOG = new double[0]; double[] wSIFT = new double[0]; alglib.lda.fisherlda(xyHOG, NPoints, NVarsHOG, NClasses, ref info, ref wHOG, null); alglib.lda.fisherlda(xySIFT, NPoints, NVarsSIFT, NClasses, ref info, ref wSIFT, null); lda.projectingVectorHOG = wHOG; lda.projectingVectorSIFT = wSIFT; Stream SaveFileStream = File.Create(LDA_FILE_NAME); BinaryFormatter serializer = new BinaryFormatter(); serializer.Serialize(SaveFileStream, lda); SaveFileStream.Close(); } }