function [U_hat, S_hat] = RPCA_gd_implicit(X, lambda, tol, maxIter)



[m n] = size(X);
if nargin < 2
    lambda = 1 / sqrt(m);
end

if nargin < 3
    tol = 1e-6;
elseif tol == -1
    tol = 1e-6;
end

if nargin < 4
    maxIter = 10000;
elseif maxIter == -1
    maxIter = 10000;
end


%%
U = 1e-4*randn(n,n);
Sp = 1e-4*randn(n); Sm = Sp;
%
mu_U = .0001; mu_S = mu_U/lambda;
 diff = 1;
 temp = U*U' + Sp.*Sp - Sm.*Sm - X; obj_old = norm(temp,'fro')^2;
i = 1; dist = []; Obj = [];
while i < maxIter & diff > tol
    i = i+ 1;
    % compute gradient
    gradU = (temp + temp')*U + lambda*U;
    gradSp = 2*temp.*Sp;
    gradSm = -2*temp.*Sm;
    %gradient descent
    U = U - mu_U*gradU;
    Sp = Sp - mu_S*gradSp;
    Sm = Sm - mu_S*gradSm;
    temp = U*U' + Sp.*Sp - Sm.*Sm - X;
    obj = norm(temp,'fro')^2;
end
U_hat = U;
S_hat = Sp.*Sp - Sm.*Sm;
