Code covered by the BSD License  

Highlights from
Scatterplot with points indexes

image thumbnail
from Scatterplot with points indexes by Francesco Montorsi
Like standard scatterplot() function but adds indexes of the data points.

scatterplot_with_indexes(signal, titlestr, plotstring, varargin)
% scatterplot_with_indexes()
% ==========================
%
% by Francesco Montorsi, 24/08/2009
%
% Usage example:
%{
   channel_symbols = modulate(modem.qammod('M',16,'SymbolOrder','Gray'),floor(16*rand(1,30)));
   scatterplot_with_indexes(channel_symbols,'16-QAM','b.','MarkerSize',20)
%}
function scatterplot_with_indexes(signal, titlestr, plotstring, varargin)

    % argument check
    % --------------

    if nargin < 2
        titlestr = 'Complex channel symbols';
    end

    if nargin < 3 || isempty(plotstring)
        plotstring = 'b.';
    end

    
    % plot the scatter plot
    % ---------------------
    
    % code adapted from MATLAB's scatterplot() function:
    if isreal(signal)
        error('The given signal should be complex');
    end
    
    [rows,cols]=size(signal);
    if rows > 1
        error('The given signal should be a vector, not a matrix');
    end

    set(gcf, 'Name', titlestr);

    % remove any subplot and reset the current figure (unless hold is on;
    % in that case the caller may want to superimpose our output on a
    % previous graphic)
    if ishold == 0
        clf;
    end
    
    % do the real plot
    show_current_figure_fullscreen();
    plot(real(signal).', imag(signal).', plotstring, varargin{:});
    hold on;
    grid on;

    % Adjust the limits
    limFact = 1.07;
    limits = max(max(abs(axis)),max(max(abs(signal)))*limFact);
    axis equal;
    axis([-limits limits -limits limits]);

    % Label the plot
    ylabel('Quadrature');
    xlabel('In-Phase');
    title(titlestr);

    % only add indexes if the number of points is limited;
    % otherwise only a chaotic image would result
    if length(signal) < 32
        % to avoid that indexes of duplicated points overlap on the figure
        % making it harder to read the different indexes, group duplicated
        % points building an array cmplx_points of unique points and a cell
        % array cmplx_points_desc of the associated descriptions
        npoints = 1;
        to_skip = [];
        cmplx_points = zeros(1,length(signal));     % preallocation
        for ii=1:length(signal)
            if find(to_skip == ii)
                continue;       % we already grouped this point with another
                                % coincident point...
            end

            duplicates_idx = find(signal == signal(ii));
            assert(length(duplicates_idx) >= 1);
            assert(duplicates_idx(1) == ii);

            % store this point in the final array in any case:
            cmplx_points(npoints) = signal(ii);

            if length(duplicates_idx) == 1
                % there is no real duplicate of this point in the scatterplot
                % since duplicates_idx(1) == ii!
                cmplx_points_desc{npoints} = int2str(ii);
            else
                % create the description for all duplicated points:
                cmplx_points_desc{npoints} = '';
                for jj=1:length(duplicates_idx)
                    cmplx_points_desc{npoints} = ...
                        strcat(cmplx_points_desc{npoints},int2str(duplicates_idx(jj)),',');
                end

                % remove final comma:
                cmplx_points_desc{npoints} = cmplx_points_desc{npoints}(1:end-1);

                % mark all other duplicates as skippable:
                to_skip = [to_skip duplicates_idx(2:end)];
            end

            npoints = npoints + 1;
        end

        % add to the plot indexes of the various channel symbols
        assert(npoints-1 == length(cmplx_points_desc));
        for ii=1:npoints-1
            text(real(cmplx_points(ii))*1.1, imag(cmplx_points(ii))*1.1, ...
                 cmplx_points_desc{ii});
        end
    end
end

Contact us at files@mathworks.com