% clear all;
% close all;
% clc;

%model input parameters 
L = 1.46; %hollow fiber length [m]
d = 0.75e-3; %hollow fiber diameter [m]
A = 9.612e-12; %water permeability constant [m/(Pa*s)]
B = 3.0e-07; %salt permeability constant [m/s]
N = 60; %discretization points axial direction [-]
Nr = 100; %number fibers per module [-]
Qf = 1.325e-5/3:1.325e-5/3:6*1.325e-5/3; %feed flowrate [m^3/s]
p0 = 2*10^(5):2*10^(4):8*10^5; %inlet pressure [Pa]
Cf = 5; %feed concentration [mol/m^3]
pp0 = 1.013*10^5; %permeate pressure [Pa]
dx = L/(N-1); %discretization difference [m]
x = 0:dx:L; %axial position of discretization points [m]
r = d/2; %inner fiber radius [m]
Rg = 8.314; %ideal gas constant [J/(mol*K)]
eta = 1.0016e-3; %dynamic viscosity [Js/m^3]
rho = 998.21; %solvent density [kg/m3]
T = 293.15; % Temperature [K]
Ds = 0.75e-9; %Diffusion coefficient [m^2/s]

%model variables
cb = ones(1,N); %salt bulk concentration [mol/m^3]
cp = ones(1,N); %salt permeate concentration [mol/m^3]
cm = ones(1,N); %membrane salt concentration [mol/m^3]
dPi = ones(1,N); %osmotic pressure difference [j/m^3] or [Pa]
p = ones(1,N); %pressure inside fiber [j/m^3] or [Pa]
v = ones(1,N); %velocity in tube [m/s]
Jw = ones(1,N); %water flux [m/s]
kle = ones(1,N); %initial mass transfer coefficient [m/s]
k = ones(1,N); %corrected mass transfer coefficient [m/s]

counter = 1; %loop counter (only used for multiple length, flow rates or pressures)

for z=1:1:size(Qf,2)
    for i=1:1:size(L,2)
        for j=1:1:size(p0,2)
%precalculations
Area = pi*r^2; % hollow fiber crosssection [m^2]
Qfs = Qf(z)/Nr; % flowrate per fiber [m3/s]
v0 = Qfs/Area; %inlet velocity [m/s]
Re = rho*v0*d/eta; %Reynolds number [-]
k0 = (1.62*Ds/d)*(v0*d*d/Ds/L(i))^(0.33); %inital value mass transfer coefficient [m/s]

%simulation parameters
par(1) = L(i);
par(2) = d;
par(3) = N;
par(4) = A;
par(5) = B;
par(6) = eta;
par(7) = rho;
par(8) = Ds;
par(9) = Rg;
par(10) = T;
par(11) = p0(j);
par(12) = v0;
par(13) = Cf;
par(14) = pp0;

%initialization of variables
if counter==1 %start vector for first iteration
x0=ones(1,N*9);
x0(1,2*N+1:N*3)=ones(1,N)*0.25; 
x0(1,N+1:N*2)=cm/Cf; 
else %use solution of previous iteration as start vector
x0=ones(1,N*9);
x0(1,1:N)=cb/Cf;
x0(1,N+1:N*2)=cm/Cf;
x0(1,2*N+1:N*3)=cp/Cf;
x0(1,3*N+1:N*4)=dPi/p0(j)/0.1; 
x0(1,4*N+1:N*5)=(p+p0(j)-p0(j-1))/p0(j);
x0(1,5*N+1:N*6)=v/v0;
x0(1,6*N+1:N*7)=Jw/10^(-5);
x0(1,7*N+1:N*8)=k/k0;
x0(1,8*N+1:N*9)=kle/k0;
end

fun=@(x0) HollowFiber(x0,par);
options = optimoptions('fsolve','Algorithm','levenberg-marquardt','TolFun',1e-10,'TolX',1e-10,'MaxIter',100,'MaxFunEvals',999999,'Display','iter');
[res,fval] = fsolve(fun,x0,options);

cb = res(1,1:N)*Cf;
cm = res(1,N+1:N*2)*Cf;
cp = abs(res(1,2*N+1:N*3)*Cf);
dPi = res(1,3*N+1:N*4)*p0(j)*0.1;
p = res(1,4*N+1:N*5)*p0(j);
v = res(1,5*N+1:N*6)*v0;
Jw = res(1,6*N+1:N*7)*10^(-5);
k = res(1,7*N+1:N*8)*k0;
kle = res(1,8*N+1:N*9)*k0;

Js = Jw.*cp;  %salt flux [mol/m^2s]
Qrs = v(end)*pi*r^2; %retentate stream [m^3/s]
Qps = Qfs-Qrs; %permeate stream [m^3/s]
Qr = Qrs*Nr;
Qp = Qps*Nr;
Rec = Qp/Qf(z);
dbl = Ds./k;

Retavg(i,z,j) = 1-sum(Jw.*cp)/sum(Jw)/Cf; %average Retention [-]
Fluxavg(i,z,j) = sum(Jw)/size(Jw,2)*1000*60*60; %average Flux [LMH]
pin(i,z,j) = p(1); %inlet Pressure [Pa]
pout(i,z,j) = p(end); %outlet Pressure [Pa]
pavg(i,z,j) = sum(p)/size(p,2); %average Pressure [Pa]
CmAVG(i,z,j)=sum(cm)/size(cm,2); %average Membrane Surface Concentration [Pa]
Cmmax(i,z,j)=cm(end); %outlet Membrane Surface Concentration [Pa]

couner=counter+1;
if counter==size(p0,2)+1 %reset counter
counter=1;
end

        end
    end
end

function Fs = HollowFiber(x,par) %%variables x, parameters p
%p
L = par(1); %membrane length [m]
d = par(2); %membrane diameter [m]
N = par(3); %discretization points [-]
A = par(4); %membrane solvent permeability [m/(Pa*s)]
B = par(5); %membrane salt permeability [m/s]
eta = par(6); %solvent viscosity [Js/m^3]
rho = par(7); %solvent density [kg/m3]
Ds = par(8); %Diffusion constant salt [m^2/s]
Rg = par(9); %ideal gas constant [J/(mol*K)]
T = par(10); %temperature [K]
p0 = par(11); %inlet pressure [Pa]
v0 = par(12); %inlet velocity [m/s]
Cf = par(13); %feed concentration [mol/m^3]
pp0 = par(14); %permeate pressure [Pa]

k0 = (1.62*Ds/d)*(v0*d*d/Ds/L)^0.33; %initial mass transfer coefficient [m/s]
r = d/2; %radius [m]
dx = L/(N-1); %discretization difference [m]
z = 0:dx:L; %axial position of discretization points [m]
z(1) = dx*10^(-1); %first point shift to prevent division by zero
Re = rho*v0*d/eta; %Reynolds number [-]
Sc = eta/rho/Ds; %Schmidt number [-]

%x
cb = x(1:N)*Cf;
cm = x(N+1:N*2)*Cf;
cp = abs(x(2*N+1:N*3)*Cf);
dPi = x(3*N+1:N*4)*p0*0.1;
p = x(4*N+1:N*5)*p0;
v = x(5*N+1:N*6)*v0;
Jw = x(6*N+1:N*7)*10^(-5);
k = x(7*N+1:N*8)*k0;
kle = x(8*N+1:N*9)*k0;

%scaling factors
Jws = A*(p0-pp0); 
vs = Jws*2/r;   
dpdxs = 8*eta*v0/r^2; 
cbs = vs*Cf; 
dPis = 2*Rg*T*Cf;

%%equation system
%continuity and pressure loss
F{1} = vs^(-1)*(((v(2:end)-v(1:end-1))./dx)+(2/r).*(Jw(1:end-1)+Jw(2:end))/2);
F{2} = dpdxs^(-1)*(((p(2:end)-p(1:end-1))./dx)+64*eta./(rho*(v(1:end-1)+v(2:end))/2*d).*rho.*(((v(1:end-1)+v(2:end))/2).^2)./4/r-rho*9.81);
F{3} = cbs^(-1)*((cb(2:end)-cb(1:end-1))./dx.*(v(1:end-1)+v(2:end))/2+((v(2:end)-v(1:end-1))./dx).*(cb(1:end-1)+cb(2:end))/2+(2/r)*(Jw(1:end-1)+Jw(2:end))/2.*((cp(1:end-1)+cp(2:end))/2));
%membrane transport
F{4} = Jws^(-1)*(Jw-A*(p-pp0-dPi));
%F{5} = Cf^(-1)*((-cm+(cb(1)-cp).*exp(Jw./(abs(k)))+cp)); %standard film model
F{5} = Jws.^(-1)/100*(abs(k).*(cm-cb(1))-Jw.*(cm-cp));%curvature film model
F{6} = Jws.^(-1)*(Jw.*cp-B*(cm-cp));
%mass transfer boundary layer
%standard Leveque
%F{7} = k0^(-1)*(abs(k)-(1.62*Ds/d).*((v0*d*d./L/Ds).^0.333)); %average
%F{7} = k0^(-1)*(abs(k)-(1.08*Ds/d).*((v0*d*d./z/Ds).^0.333)); %local
%Newman correlation + suction correction
% F{7} = k0^(-1)*(abs(kle)-(1.62*((v0*d*d./L/Ds).^(0.333))-1.2-0.28*((v0*d*d./L/Ds).^(-0.333)))*Ds/d);
% Jwavg=sum(Jw)/size(Jw,2);
% Psi=Jwavg./abs(kle);
% Phi=Psi+(1+0.26*Psi.^(1.4)).^(-1.7);
% F{12} = k0^(-1)*(Phi.*kle-k);
%Newman correlation + suction correction + recovery correction
F{7} = k0^(-1)*(abs(kle)-(1.62*((v0*d*d./L/Ds).^(0.333))-1.2-0.28*((v0*d*d./L/Ds).^(-0.333)))*Ds/d);
Jwavg=sum(Jw)/size(Jw,2);
Psi=Jwavg./abs(kle);
Phi=Psi+(1+0.26*Psi.^(1.4)).^(-1.7);
Cor=1.016-0.27*(v0^(-0.9871)*Jwavg^0.9225*d^(-1.1386)*L^1.074*Ds^0.0646);
F{12} = k0^(-1)*(Phi.*kle*Cor-k);
F{8} = dPis^(-1)*(dPi-2*Rg*T*(cm-cp));
%boundary conditions
F{9} = 10^3*(cb(1)- Cf);
F{10} = 10^3*(p(1) - p0);
F{11} = 10^3*(v(1) - v0);

for i=1:12
[a, b]=size(F{i});
F{i} = reshape(F{i},[a*b 1]);
end

Fs=[F{1};F{2};F{3};F{4};F{5};F{6};F{7};F{8};F{9};F{10};F{11};F{12}];%];%;F{13};F{14}];
end

