function pnew=permutation(p)
	% will generate a new permutation from the old one
	% in such a way that new one will be lexicographically  smaller.
	%
	% If one wants all possible permutation, she
	% must prearrange elements of the permutation vector p
	% in ascending order for the first input
	%
	% elements of the input vector might be not unique
	%
	% see "The Art of Computer Programming, Volume 4: 
	% Generating All Tuples and Permutations" by Donald Knuth
	% for the discussion of the algorithm
	%
	% This implementation is optimized for matlab and avoid cycles 
	% which are costly during execution 
	
	N=length(p);
	indxs=1:N; % indexes of permutation elements

	% looking for the largest k where p(k) < p(k+1)
	k_candidates=indxs( p(1:N-1) < p(2:N) );
	if ( isempty(k_candidates) )
		% no such k is found thus nothing to permute
		pnew= p;  % we must check at the caller for this special case
		return; % all possible permutations are done
	end
	k=k_candidates(end) ; % note special operator 'end' the last element of array

	% find the largest l such that p(k) < p(l) 
	% since we are  here at least k+1 satisfies
	indxs=indxs(k+1:end); % we need to truncate possible indexes list
	l_candidates=indxs( p(k) < p (k+1:end) );
	l=l_candidates(end);

	tmp=p(l); p(l)=p(k); p(k)=tmp; % swap p(k) and p(l)

	%reverse the sequence between p(k+1) and p(end)
	p(k+1:end)=p( end:-1:k+1 );
	pnew=p;
end
	



