MATLAB | 散布図を描画するときに範囲外の散布点に自動的にラベルを付ける方法は?

この記事では、座標領域の範囲を超えた点に自動的にラベルを付ける方法について説明します。たとえば、次のとおりです。

図の右側の赤い十字は、横座標が範囲を超える点の縦座標を表し
、もちろん下の赤い十字は縦座標が範囲を超える点の横座標を表します。

この記事で使用する自作ツールの機能はscatterOOR記事の最後に載せますので、まずは使い方を説明します。

基本的な使い方

散布図を描画するために次のコードを作成するとします。

clc; clear; close all
rng(1)
% 生成随机点(Generate random points)
mu = [2 3; 6 7; 8 9];
S  = cat(3,[1 0; 0 2],[1 0; 0 2],[1 0; 0 1]);
r1 = abs(mvnrnd(mu(1,:),S(:,:,1),100));
r2 = abs(mvnrnd(mu(2,:),S(:,:,2),100));
r3 = abs(mvnrnd(mu(3,:),S(:,:,3),100));
% 绘制散点图(Draw scatter chart)
hold on
propCell = {
    
    'LineWidth',1.2,'MarkerEdgeColor',[.3,.3,.3],'SizeData',60};
scatter(r1(:,1),r1(:,2),'filled','CData',[0.40 0.76 0.60],propCell{
    
    :});
scatter(r2(:,1),r2(:,2),'filled','CData',[0.99 0.55 0.38],propCell{
    
    :});
scatter(r3(:,1),r3(:,2),'filled','CData',[0.55 0.63 0.80],propCell{
    
    :});
% 增添图例(Draw legend)
lgd = legend('scatter1','scatter2','scatter3');
lgd.Location = 'northwest';
lgd.FontSize = 14;
% 坐标区域基础修饰(Axes basic decoration)
ax=gca; grid on
ax.FontName   = 'Cambria';
ax.Color      = [0.9,0.9,0.9];
ax.Box        = 'off';
ax.TickDir    = 'out';
ax.GridColor  = [1 1 1];
ax.GridAlpha  = 1;
ax.LineWidth  = 1;
ax.XColor     = [0.2,0.2,0.2];
ax.YColor     = [0.2,0.2,0.2];
ax.TickLength = [0.015 0.025];
% 隐藏轴线(Hide XY-Ruler)
pause(1e-6)
ax.XRuler.Axle.LineStyle = 'none';
ax.YRuler.Axle.LineStyle = 'none';


ax.XLim = [-2,10];
ax.YLim = [2,14];

コードの最後に次の行を直接追加します。

scatterOOR()

または

scatterOOR(gca)

つまり、最初のパラメータは座標領域オブジェクトであり、省略可能です。直接的かつ単純な呼び出しにより、次の効果が得られます。

範囲外の点描に派手なドットを使用する場合はどうですか? scatterこれは、次の 2 つの方法のように、グラフィック プロパティをカスタマイズすることで実現できます。

scatterOOR('filled','CData',[0,0,.8],'LineWidth',1.5,...
    'MarkerEdgeColor',[.5,.5,.5],'SizeData',120,'Marker','s')
scatterOOR(gca,'filled','CData',[0,0,.8],'LineWidth',1.5,...
    'MarkerEdgeColor',[.5,.5,.5],'SizeData',120,'Marker','s')

範囲外のポイントのデフォルトの凡例名が OOR であることがわかりますが、この名前を変更するにはどうすればよいでしょうか?

これも非常に簡単で、たとえば、名前を に変更するにはLALALA、コードの最後に次の 2 行を追加します。

OORHdl = findobj(ax,'Tag','SLANOOR');
OORHdl.DisplayName = 'LALALA';

ツール機能の完全なコード

非常に短く、40 行未満です。

function scatterOOR(ax,varargin)
% Copyright (c) 2023, Zhaoxu Liu / slandarer
if nargin < 1
    ax = gca;
end
if ~isa(ax,'matlab.graphics.axis.Axes')  
    varargin = [{
    
    ax}, varargin(:)'];
    ax = gca;
end
ax.NextPlot = 'add';
if isempty(varargin)
    varargin={
    
    'filled','CData',[.8,0,0],'LineWidth',1.5,...
    'MarkerEdgeColor',[.8,0,0],'SizeData',120,'Marker','x'};
end

OORHdl = findobj(ax,'Tag','SLANOOR');
if isempty(OORHdl)
    OORHdl = scatter([],[],varargin{
    
    :},'Tag','SLANOOR','DisplayName','OOR');
end
fullHdl = findobj(ax,'Type','scatter');
fullXData = [fullHdl(:).XData];
fullYData = [fullHdl(:).YData];

moveAxes();
addlistener(ax,'MarkedClean',@moveAxes);
    function moveAxes(~,~)
        tBool = fullXData >= ax.XLim(2) | fullXData <= ax.XLim(1)...
              | fullYData >= ax.YLim(2) | fullYData <= ax.YLim(1);
        tFullXData = fullXData; 
        tFullYData = fullYData;
        tFullXData(tFullXData >= ax.XLim(2)) = ax.XLim(2);
        tFullXData(tFullXData <= ax.XLim(1)) = ax.XLim(1);
        tFullYData(tFullYData >= ax.YLim(2)) = ax.YLim(2);
        tFullYData(tFullYData <= ax.YLim(1)) = ax.YLim(1);
        tFullXData = tFullXData(tBool);
        tFullYData = tFullYData(tBool);
        OORHdl.XData = tFullXData;
        OORHdl.YData = tFullYData;
    end
end

おすすめ

転載: blog.csdn.net/slandarer/article/details/131833062