function [A, b, C, X, y, Z, status] = genHardSDP(m, n, gap, NoP, NoD, dualHasInteriorFlag) %This file generates general hard instance (Strict complementary %slackness conditions fails) for SDPs % min trace CX s.t. Aop X = b X psd % input: % m, n, the size of b and C. % gap: the desired strictly complementary gap; can be 0; % NoP: the maximal rank of the primal optimum % NoD: the maximal rank of the dual optimum; % dualhasInteriorFlag(optional): set to 1 means that the dual is % guranteed to to have interior; set to 0 means the dual might not % have interior. %Output: % A hard SDP instance. with data A, b, C, optimal solution % X, y, Z % where A{i} is matrix A_i. % status == 1, successful. % status ==0, error. % Author: Hua Wei, Henry Wolkowicz % University of Waterloo % Feb 1, 2006 status =0; %default parameters if (nargin < 6) dualHasInteriorFlag =0; end if (NoP+ NoD + gap ~= n) NoD= n-NoP - gap; %error(['error on the parameters: NoP + NoD + noofGap is not equal to n']); disp(['error on the parameters: NoP + NoD + noofGap is not equal to n']); disp(['NoD is reset: NoD= n-NoP - gap']); end if (NoP<=0 | NoD <=0 | gap <0) error(['NoP, NoP should be positive and gap should be non-negative.' ... ' Check the input']); end % 1. construct Optimal X and Z. Q = zeros(n,n); while rank(Q) < n Q = rand(n,n); end Q = orth(Q); P = 1:NoP; G = NoP+1: NoP + gap ; D = NoP + gap +1 : n; Dx = diag(rand(NoP,1) * 100 ) + 0.1; Dz = diag(rand(NoD,1) * 100 ) + 0.1; X = Q(:, P) * Dx * Q(:, P)'; Z = Q(:, D) * Dz * Q(:, D)'; % 2. generate random A_i A=cell(m,1); lo= -10000; up= 10000; Y1 = generateY1(gap,lo,up); Y2 = rand(NoD, NoP)*(up-lo)+lo; %zeroIdx = find(sum(abs(Y2))==0); while ( Q(:,D)*Y2 == 0 ) 'repeat here line 48 in genHardSDP' Y2 = rand(NoD, NoP)*(up-lo)+lo; zeroIdx = find(sum(abs(Y2))==0); end Y3 = rand(NoD, gap) * (up-lo) + lo; Y4 = rand(NoD, NoD) * (up-lo) + lo; Y4 = (Y4+Y4')/2; YY = [ zeros(NoP, NoP) zeros(NoP, gap) Y2' zeros(gap, NoP) Y1 Y3' Y2 Y3 Y4]; A{1} = Q * YY * Q'; AQ = zeros(n*NoP, m); tmp= A{1}*Q(:,P); AQ(:,1) = tmp(:); i =2; while (i<= m) if dualHasInteriorFlag & i==2 %setting this to 1 will not generate positive matrix newMatrix = rand(n,n)*2*sqrt(up)+ (-sqrt(abs(lo))); newMatrix = (newMatrix * newMatrix' + eye(n))/n; else newMatrix = rand(n,n)*(up-lo)+lo; newMatrix = (newMatrix + newMatrix')/2; end tmp = newMatrix*Q(:,P); AQ(:,i) = tmp(:); if (rank(AQ(:,1:i)) == i) A{i} = newMatrix; i = i+1; end end b = zeros(m,1); for i=1:m b(i) = trace(A{i}* X); end C = zeros(n,n); y = rand(m,1)*(up-lo)+lo; Tmp = zeros(n,n); for i=1:m Tmp = Tmp + A{i} * y(i); end C = Tmp + Z; status =1; return; function Y1 = generateY1(gap, lo, up ) Y1 = rand(gap,gap)*(up-lo) + lo; %genearate Y1 in the range of (up-lo) Y1= (Y1+Y1')/2; Y1 = Y1 + rand * ( 10 * (up-lo) )* eye(gap); tol = 0.1; while min(eig(Y1))< tol Y1 = rand(gap,gap)*(up-lo) + lo; Y1= (Y1+Y1')/2; Y1 = Y1 + rand * (10* (up-lo) ) * eye(gap); end return;