Face detection using color feature - matlab

I am trying to detect faces in my picture. So I found a code that do this, but depending on my picture-input sometimes it finds the faces and for other pictures it doesn't work.
So I thought it because of the face's color of person that is on the picture. So when I change the thresholds value sometimes it make to work.
My thresholds value:
%Threshold
hlow = 0.0; hhigh = 0.4;
slow = 0.3; shigh = 0.8;
vlow = 0.4; vhigh = 0.9;
Blob_Threshold = 120;
Edge_Threshold = 650;
Edge_Tolerance = 500;
Percentage_Threshold = 35;
Tolerance = 0.25;
and it here is my code :
function [Faces_List inx_face] = FaceDetection(img)
%----------------Initialization----------------------
Temp_img = img;
img_height = size(Temp_img,1); % tedade satr
img_width = size(Temp_img,2); % tedade sotoona
Temp_img = im2double(Temp_img);
Skin = zeros(img_height,img_width);
%Threshold
hlow = 0.0; hhigh = 0.4;
slow = 0.3; shigh = 0.8;
vlow = 0.4; vhigh = 0.9;
Blob_Threshold = 120;
Edge_Threshold = 650;
Edge_Tolerance = 500;
Percentage_Threshold = 35;
Tolerance = 0.25;
goldenRatio = (1+sqrt(5))/2;
%----------------Convert Color Space From RGB2HSV----
Temp_img = rgb2hsv(Temp_img);
for i = 1:img_height
for j = 1:img_width
H = Temp_img(i,j,1);
S = Temp_img(i,j,2);
V = Temp_img(i,j,3);
bh = H >= hlow && H <= hhigh;
bs = S >= slow && S <= shigh;
bv = V >= vlow && V <= vhigh;
if (bh && bs && bv)
Skin(i,j) = 1;
end
end
end
figure;imshow(Skin);title('Skin Color Detection');
%----------------Initialization----------------------
%Skin_Blob = bwconncomp(Skin,8);
[Skin_Blob,Blob_Number] = bwlabel(Skin);
BlobData = regionprops(Skin_Blob,'all');
%Blob_Number = Skin_Blob.NumObjects;
inx_face = 0;
Faces_List = [];
%----------------Main Face Detection-----------------
for i = 1:Blob_Number
if (BlobData(i).Area > Blob_Threshold)
myFace = BlobData(i).Image;
figure;imshow(myFace);
%pause(1);
myHeight = size(myFace,1);%height
myWidth = size(myFace,2);%width
b1 = (myHeight/myWidth) >= goldenRatio - Tolerance;
b2 = (myHeight/myWidth) <= goldenRatio + Tolerance;
b3 = (myWidth/myHeight) >= goldenRatio - Tolerance;
b4 = (myWidth/myHeight) <= goldenRatio + Tolerance;
Percentage_skin = (sum(myFace(:)) / (myHeight * myWidth)) * 100;
b5 = Percentage_skin > Percentage_Threshold;
boundingBox = BlobData(i).BoundingBox;
x1 = fix(boundingBox(1));
y1 = fix(boundingBox(2));
x2 = fix(boundingBox(3));
y2 = fix(boundingBox(4));
edgeFace = imcrop(img,[x1 y1 x2 y2]);
imGray = rgb2gray(edgeFace);
imEdge = edge(imGray,'sobel');
sumEdge = sum(imEdge(:));
b6 = sumEdge >= Edge_Threshold - Edge_Tolerance;
b7 = sumEdge <= Edge_Threshold + Edge_Tolerance;
if (((b1 && b2) || (b3 && b4)) && b5 && (b6 && b7))
inx_face = inx_face + 1;
Faces_List(inx_face).x1 = x1;
Faces_List(inx_face).y1 = y1;
Faces_List(inx_face).x2 = x2;
Faces_List(inx_face).y2 = y2;
end
end %end if
end %for i
end%Function

Related

the script works normally for few data but if it accepts a matrix with a lot of data it takes too long time

That script(matlab) works normally and fast for few data but if it accepts a matrix with a lot of data it takes too long time >1hr it run with no error but very very slow. What is the reason and what i can do for that (what are the main factors that make a program slow)
clear;clc;close all;
pref=input('Please enter file prefix: ','s');
fn=[pref '.mhk'];
fr=fopen(fn,'r');
k=0;
error = false;
t = fgetl(fr);
XTH = [];
Yed = [];
while ~feof(fr)
t = fgetl(fr);
[temp,~]=sscanf(t,'%f');
if ~error
k = k + 1;
XTH(k) = temp(1);
Yed(k) = temp(2);
end
end
x = [XTH(1)];
y = [Yed(1)];
XTH=[x XTH];
Yed = transpose([y Yed]);
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
n = length(XTH);
l = 0;
k = 0;
Vmin = 100000000;
r=0;
for u1 = 1:XTH(end)
l = l + 1;
if ismember(u1,XTH)==1
u1 = u1 + 0.1;
end
if u1>=XTH(1)+1 && u1< XTH(end)-1
for u2 = u1:XTH(end)
k = k + 1;
if u2 == u1
u2 = u2 + 1;
end
if ismember(u2,XTH)
u2 = u2 + 1;
end
XTH = [(XTH) u1 u2];
XTH = sort(XTH);
num1 = find(XTH==u1);
num2 = find(XTH==u2);
XTH = XTH(XTH~=u1);
XTH = XTH(XTH~=u2);
a11 = XTH(1:num1);
a12 = repelem(u1,length(XTH)-num1);
a1 = transpose([a11, a12]);
a2 = ones(n,1);
a31 = transpose(zeros(num1,1));
a32 = XTH(num1+1:num2-1)-u1;
a33 = repelem(u2-u1,length(XTH(num2:end)));
a3 = transpose([a31 a32 a33]);
a41 = transpose(zeros(num2-1,1));
a42 = XTH(num2:end)-u2;
a4 = transpose([a41 a42]);
A = [a1 a2 a3 a4];
AtA = transpose(A)*A;
B = Yed;
AtB = transpose(A)*B;
if det(AtA)==0
continue
end
if det(AtA)<1e-3
continue
end
solution = linsolve(AtA, AtB);
alpha1 = solution(1,1);
beta1 = solution(2,1);
alpha2 = solution(3,1);
alpha3 = solution(4,1);
beta2 = (alpha1*u1) + beta1 - (alpha2*u1);
beta3 = (alpha1*u1) + beta1 + alpha2*(u2-u1) - (alpha3*u2);
dy1 = 0;
dy2 = 0;
dy3 = 0;
Dx = XTH(end)-XTH(1);
width = 10;
for j = 1:num1
dy1 = dy1 + abs((Yed(j)-(alpha1*XTH(j)+beta1)));
end
for j = num1:num2-1
dy2 = dy2 + abs((Yed(j) - (alpha2*XTH(j)+beta2)));
end
for j = num2:n
dy3 = dy3 + abs((Yed(j) - (alpha2*XTH(j)+beta2)));
end
V(l+k) = Dx*width*(1/length(Yed))*(dy1+dy2+dy3);
if V(l+k) < Vmin && V(l+k)~=0
aa1 = alpha1;
aa2 = alpha2;
aa3 = alpha3;
bb1 = beta1;
bb2 = beta2;
bb3 = beta3;
U1 = u1;
U2 = u2;
Vmin = V(l+k);
end
end
end
end
plot(transpose(XTH), Yed, 'k')
daspect([10,1,1]);
% ax = gca;
% ax.XLim = [XTH(1) XTH(end)];
hold on;
grid on;
x11 = XTH(1);
x21 = U1;
y11 = aa1*x11 + bb1;
y21 = aa1*x21 + bb1;
plot([x11,x21],[y11,y21], 'r')
x21 = U1;
x22 = U2;
y21 = aa2*x21 + bb2;
y22 = aa2*x22 + bb2;
plot([x21,x22],[y21,y22], 'r')
x31 = U2;
x32 = XTH(end);
y31 = aa3*x31 + bb3;
y32 = aa3*x32 + bb3;
plot([x31,x32],[y31,y32], 'r')
%line(U1,aa1*U1 + bb1)
disp('Line equation 1:')
line1 = ['y = ', num2str(aa1),'*x + ',num2str(bb1)];
disp(line1)
disp('Line equation 2:')
line2 = ['y = ', num2str(aa2),'*x + ',num2str(bb2)];
disp(line2)
line3 = ['y = ', num2str(aa3),'*x + ',num2str(bb3)];
disp(line3);
vol = [num2str(Vmin),' m^3'];
disp('Minimum volume achieved:')
disp(vol)

How to get rid of "Assignment has more non-singleton rhs dimensions than non-singleton subscripts"

I am getting an error at x(i,:) = x(i-1,:).*(I+a.*dt)'+b.*dt; ... I have tried making the x a whole number to try to limit the decimals. x was originally tmax/dt. Any help/ guidance to get this program to run would be great!
%{
Ocean Thermal Systems - Project 1
2-D Transient Heat Conduction through Aluminum
%}
%Remove all variables, globals and functions
clear all
%Clear the command window
clc
%Input parameters
% l: dx=dy=0.01m
% h: convective heat transfer coefficient (W/m^2.deg.C)
% k: thermal conductivity of the material (W/m.deg.C)
% c: specific heat (J/kgK)
% p: density (Kg/m^3)
% alpha: thermal diffusivity of the material (m^2/s)
% To: initial temperature of the material (deg. C)
% Tinf: convective temperature (deg. C)
% Ts: bottom surface temperature (deg. C)
l = 0.01;
h = 30;
k = 170;
%c = 870;
p = 2800;
alpha = 6.98e-5;
To = 28;
Tinf = 28;
Ts = 90;
%Create time intervals
dt = 0.357;
dtb = 50;
tmax = 300;
Na = tmax/dt;
Nb = tmax/dtb;
ta = linspace(0,tmax,Na);
tb = linspace(0,tmax,Nb);
% Create A matrix
r = -8.8e-4;
v = -5.9e-4;
g = -1.8e-3;
a = zeros(28,28);
a(1,:) = 90;
a(2,:) = 90;
a(3,:) = 90;
a(4,:) = 90;
a(5,:) = 90;
a(6,:) = 90;
a(7,:) = 90;
a(8,:) = 90;
a(9,1) = 1; a(9,9) = g; a(9,10) = .5;
a(10,1) = .25; a(10,2) = .5; a(10,10) = r; a(10,11) = .25;
a(11,10) = .16; a(11,11) = v; a(11,12) = .32; a(11,13) = .32;
a(12,4) = .32; a(12,11) = .32; a(12,12) = v; a(12,13) = .16; a(12,18) = .16;
a(13,5) = .5; a(13,12) = .25; a(13,13) = r; a(13,15) = .5;
a(14,6) = .32; a(14,13) = .16; a(14,14) = v; a(14,15) = .32; a(14,19) = .16;
a(15,7) = .32; a(15,10) = .16; a(15,14) = .32; a(15,15) = v; a(15,20) = .16;
a(16,8) = .5; a(16,15) = .5; a(16,16) = g;
a(17,11) = .25; a(17,17) = r; a(17,18) = .5; a(17,21) = .25;
a(18,12) = .25; a(18,17) = .5; a(18,18) = r; a(18,22) = .25;
a(19,14) = .25; a(19,19) = r; a(19,20) = .5; a(19,23) = .25;
a(20,15) = .25; a(20,19) = .25; a(20,20) = r; a(20,27) = .25;
a(21,17) = .25; a(21,18) = r; a(21,22) = .5; a(21,25) = .25;
a(22,18) = .25; a(22,21) = .5; a(22,22) = r; a(22,26) = .25;
a(23,19) = .25; a(23,23) = r; a(23,24) = .5; a(23,27) = .25;
a(24,20) = .25; a(24,23) = .5;a(24,24) = r; a(24,28) = .25;
a(25,21) = .5; a(25,25) = g; a(25,26) = .5;
a(26,22) = .5; a(26,25) = .5; a(26,26) = g;
a(27,23) = .5; a(27,27) = g; a(27,28) =.5;
a(28,24) = .5; a(28,27) = .5; a(28,28) = g
%Create matrix for each node
T1 = zeros(tmax,1);
T2 = zeros(tmax,1);
T3 = zeros(tmax,1);
T4 = zeros(tmax,1);
T5 = zeros(tmax,1);
T6 = zeros(tmax,1);
T7 = zeros(tmax,1);
T8 = zeros(tmax,1);
T9 = zeros(tmax,1);
T10 = zeros(tmax,1);
T11 = zeros(tmax,1);
T12 = zeros(tmax,1);
T13 = zeros(tmax,1);
T14 = zeros(tmax,1);
T15 = zeros(tmax,1);
T16 = zeros(tmax,1);
T17 = zeros(tmax,1);
T18 = zeros(tmax,1);
T19 = zeros(tmax,1);
T20 = zeros(tmax,1);
T21 = zeros(tmax,1);
T22 = zeros(tmax,1);
T23 = zeros(tmax,1);
T24 = zeros(tmax,1);
T25 = zeros(tmax,1);
T26 = zeros(tmax,1);
T27 = zeros(tmax,1);
T28 = zeros(tmax,1);
%{
T1(1) = 28;
T2(1) = 28;
T3(1) = 28;
T4(1) = 28;
T5(1) = 28;
T6(1) = 28;
T7(1) = 28;
T8(1) = 28;
T9(1) = 28;
T10(1) = 28;
T11(1) = 28;
T12(1) = 28;
T13(1) = 28;
T14(1) = 28;
T15(1) = 28;
T16(1) = 28;
T17(1) = 28;
T18(1) = 28;
T19(1) = 28;
T20(1) = 28;
T21(1) = 28;
T22(1) = 28;
T23(1) = 28;
T24(1) = 28;
T25(1) = 28;
T26(1) = 28;
T27(1) = 28;
T28
%}
x = ones(N,1)*28
%create matrices
m = 0.02475;
b = 0.01584
c = 0.024706;
d = 0.049;
b = [0;0;0;0;0;0;0;0;d;m;b;b;m;b;b;d;m;m;m;m;m;c;c;c;d;d;d;d]
I = eye(28);
%
for i = 2:Na
x(i,:) = x(i-1,:).*(I+a.*dt)'+b.*dt;
T1(i) = 28;
T2(i) = 28;
T3(i) = 28;
T4(i) = 28;
T5(i) = 28;
T6(i) = 28;
T7(i) = 28;
T8(i) = 28;
T9(i) = 28;
T10(i) = 28;
T11(i) = 28;
T12(i) = 28;
T13(i) = 28;
T14(i) = 28;
T15(i) = 28;
T16(i) = 28;
T17(i) = 28;
T18(i) = 28;
T19(i) = 28;
T20(i) = 28;
T21(i) = 28;
T22(i) = 28;
T23(i) = 28;
T24(i) = 28;
T25(i) = 28;
T26(i) = 28;
T27(i) = 28;
T28(i) = 28;
end
plot(ta,x); grid on; hold on;
A simple Google search on the error message gave the following link where the problem is very well described:
https://se.mathworks.com/matlabcentral/answers/91151-the-error-assignment-has-more-non-singleton-rhs-dimensions-than-non-singleton-subscripts-when-hap

how to Improve the speed matlab

This is my matlab code. It runs too slow and I had no clue how to improve it.
Could you help me to improve the speed?
What I would like to do is to create some random points and then remove the random points to make them similar to my target points.
syms Dx Dy p q;
a = 0;
num = 10;
x = rand(1,num);
y = rand(1,num);
figure(1)
scatter(x,y,'.','g')
%num_x = xlsread('F:\bin\test_2');% num 1024
%figure(2)
%scatter(num_x(:,1),num_x(:,2),'.','r');
q = 0;
num_q = 10;
x_q = randn(1,num_q);
y_q = randn(1,num_q);
%figure(2)
hold on;
scatter(x_q,y_q,'.','r')
for i = 1:num_q;
for j = 1:num_q;
qx(i,j) = x_q(i) - x_q(j);
qy(i,j) = y_q(i) - y_q(j);
%qx(i,j) = num_x(i,1) - num_x(j,1);
%qy(i,j) = num_x(i,2) - num_x(j,2);
%d~(s(i),s(j))
if ((qx(i,j))^2+(qy(i,j)^2))> 0.01 % find neighbours
qx(i,j) = 0;
qy(i,j) = 0;
end
end
end
for i = 1:num_q;
for j = 1:num_q;
if qx(i,j)>0&&qy(i,j)>0
q = q + exp(-(((Dx - qx(i,j))^2)+((Dy - qy(i,j))^2))/4);%exp(-(((Dx - qx(i,j))^2)+((Dy - qy(i,j))^2))/4);
end
end
end
%I = ones(num,num); % I(s) should from a grayscale image
%r = 1./sqrt(I);
for s = 1:100;
for i = 1:num;
for j = 1:num;
dx(i,j) = x(i) - x(j);
dy(i,j) = y(i) - y(j);
%d~(s(i),s(j))
if ((dx(i,j))^2+(dy(i,j)^2))> 0.05 % delta p, find neighbours
dx(i,j) = 0;
dy(i,j) = 0;
end
end
end
p = 0;
for i = 1:num;
for j = 1:num;
if dx(i,j)>0&&dy(i,j)>0
p = p + exp(-(((Dx - dx(i,j))^2)+((Dy - dy(i,j))^2))/4);
end
end
end
p = p - q;
sum = 0;
for i = 1:num;
for j = 1:num;
if dx(i,j)>0&&dy(i,j)>0;
kx(i,j) = (1/2)*(Dx-dx(i,j))*exp((-(Dx-dx(i,j))^2+(Dy-dy(i,j))^2)/4);
ky(i,j) = (1/2)*(Dy-dy(i,j))*exp((-(Dx-dx(i,j))^2+(Dy-dy(i,j))^2)/4);
end
end
end
sum_x = ones(1,num);% 1行N列0矩阵
sum_y = ones(1,num);
%fx = zeros(1,num);
for i = 1:num;
for j = 1:num;
if dx(i,j)>0&&dy(i,j)>0;
fx(i) = p*kx(i,j);% j is neighbour to i
fy(i) = p*ky(i,j);
%fx(i) = matlabFunction(fx(i));
%fy(i) = matlabFunction(fy(i));
%P =quad2d(#(Dx,Dy) fx,0,0.01,0,0.01);
%fx =quad(#(Dx) fx,0,0.01);
%fx(i) =quad(#(Dy) fx(i),0,0.01);
%Q =quad2d(#(Dx,Dy) fy,0,0.01,0,0.01);
fx(i) = double(int(int(fx(i),Dx,0,0.01),Dy,0,0.01));
fy(i) = double(int(int(fy(i),Dx,0,0.01),Dy,0,0.01));
%fx(i) = vpa(p*kx(i,j));
%fy(i) = vpa(p*ky(i,j));
%fx(i) = dblquad(#(Dx,Dy)fx(i),0,0.01,0,0.01);
%fy(i) = dblquad(#(Dx,Dy)fy(i),0,0.01,0,0.01);
sum_x(i) = sum_x(i) + fx(i);
sum_y(i) = sum_y(i) + fy(i);
end
end
end
for i = 1:num;
sum_x = 4.*sum_x./num;
sum_y = 4.*sum_y./num;
x(i) = x(i) - 0.05*sum_x(i);
y(i) = y(i) - 0.05*sum_y(i);
end
a = a+1
end
hold on;
scatter(x,y,'.','b')
The fast version of your loop should be something like:
qx = bsxfun(#minus, x_q.', x_q);
qy = bsxfun(#minus, y_q.', y_q);
il = (qx.^2 + qy.^2 >= 0.01);
qx(il) = 0;
qy(il) = 0;
il = qx>0 && qy>0;
q = sum(exp(-((Dx-qx(il)).^2 + (Dy-qy(il)).^2)/4));
%// etc. for vectorization of the inner loops

Simulate a custom function in Matlab

I'd like to simulate the following function:
l(t) = mu + Σ (1 + (t-t_i)/alpha)^(beta)
I wrote the function as follow:
function[l] = custom(m,t,H,par)
k = length(H);
n = length(t);
l = par.mu(m)*ones(n,1);
for i = 1:n
for j = 1:k
h = H{j};
h = h(h < t(i));
if ~isempty(h)
d = t(i) - h;
l(i) = l(i) + sum((1+ (d/par.alpha(m,j)))^ par.beta(m,j));
end
end
end
Now, how can I simulate this function for t=1000, par.mu= 0.5, par.alpha = 0.1, par.beta = 0.3?
I have the following code for simulation of this function but it's not efficient...How can I make it better?
function[h] = simcustom(t,par)
h = -log(rand)/par.mu;
if h < t
do5 = 1;
i = 0;
j = 0;
k = 0;
n = 1;
while true
if do5;
k = k + 1;
Lstar(k) = custom(1,h(n),{h},par); %#ok
end
j = j + 1;
U(j) = rand; %#ok
i = i + 1;
u(i) = -log(U(j))/Lstar(k); %#ok
if i == 1
Tstar(i) = u(i); %#ok
else
Tstar(i) = Tstar(i-1) + u(i);
end
if Tstar(i) > t
h = {h};
break
end
j = j + 1;
U(j) = rand;
if U(j) <= custom(1,Tstar(i),{h},par)/Lstar(k)
n = n + 1;
h = [h Tstar(i)];
do5 = true;
else
k = k + 1;
Lstar(k) = custom(1,Tstar(i),{h},par);
do5 = false;
end
end
else
h = {[]};
end
And here is the application:
par2.mu = 0.5;
par2.alpha = 0.1;
par2.beta = 0.3;
t = 1000;
h2 = simcustom(t,par2);

Perform step-by-step integral

I have this piece of code:
time = 614.4;
Uhub = 11;
HubHt = 90;
TI = 'A';
N1 = 4096;
N2 = 32;
N3 = 32;
L1 = Uhub*time;
L2 = 150;
L3 = 220;
V = L1*L2*L3;
gamma = 3.9;
c = 1.476;
b = 5.6;
if HubHt < 60
lambda1 = 0.7*HubHt;
else
lambda1 = 42;
end
L = 0.8*lambda1;
if isequal(TI,'A')
Iref = 0.16;
sigma1 = Iref*(0.75*Uhub + b);
elseif isequal(TI,'B')
Iref = 0.14;
sigma1 = Iref*(0.75*Uhub + b);
elseif isequal(TI,'C')
Iref = 0.12;
sigma1 = Iref*(0.75*Uhub + b);
else
sigma1 = str2num(TI)*Uhub/100;
end
sigma_iso = 0.55*sigma1;
%% Wave number vectors
ik1 = cat(2,(-N1/2:-1/2),(1/2:N1/2));
ik2 = -N2/2:N2/2-1;
ik3 = -N3/2:N3/2-1;
[x y z] = ndgrid(ik1,ik2,ik3);
k1 = reshape((2*pi*L/L1)*x,N1*N2*N3,1);
k2 = reshape((2*pi*L/L2)*y,N1*N2*N3,1);
k3 = reshape((2*pi*L/L3)*z,N1*N2*N3,1);
k = sqrt(k1.^2 + k2.^2 + k3.^2);
Now I should calculate
where
The procedure to calculate the integral is
At the moment I'm using this loop
E = #(k) (1.453*k.^4)./((1 + k.^2).^(17/6));
E_int = zeros(1,N1*N2*N3);
E_int(1) = 1.5;
for i = 2:(N1*N2*N3)
E_int(i) = E_int(i) + quad(E,i-1,i);
end
neglecting for the k>400 approximation. I believe that my loop is not right.
How would you suggest to calculate the integral?
I thank you in advance.
WKR,
Francesco
This is a list of correction from the more obvious to the possibly more subtle. (Indeed I start from what you wrote in the final part going upwards).
From what you write:
E = #(k) (1.453*k.^4)./((1 + k.^2).^(17/6));
E_int = zeros(1,N1*N2*N3);
E_int(1) = 1.5;
for i = 2:(N1*N2*N3)
%//No point in doing this:
%//E_int(i) = E_int(i) + quad(E,i-1,i);
%//According to what you write, it should be:
E_int(i) = E_int(i-1) + quad(E,i-1,i);
end
You could speed the whole thing up by doing
%//Independent integration on segments
Local_int = arrayfun(#(i)quad(E,i-1,i), 2:(N1*N2*N3));
Local_int = [1.5 Local_int];
%//integral additivity
E_int = cumsum(Local_int);
Moreover, if the known condition (point 2.) really is "... ( = 1.5 if k' = 0)", then the whole implementation should really be more like
%//Independent integration on segments
Local_int = arrayfun(#(i)quad(E,i-1,i), 2:(N1*N2*N3));
%//integral additivity + cumulative removal of queues
E_int = 1.5 - [0 fliplr(cumsum(fliplr(Local_int)))]; %//To remove queues