Рисовать график поверхности в Matlab, похожий на тот, который получен с помощью Gnuplot? - PullRequest
6 голосов
/ 04 марта 2011

Обновление:

Ссылка на мой тестовый набор данных

У меня есть такие данные:

10.0 11.0 0.5
10.0 12.0 0.5
10.0 14.5 0.5
10.0 16.0 0.5
10.0 18.5 0.5
10.0 19.0 0.5
10.0 19.5 0.5
10.0 20.0 0.5

Используя Gnuplot, я могу построить графикследующее изображение:

enter image description here

с использованием следующего сценария, который я написал:

set data style lines
set surface
set dgrid3d 30,30
set hidden3d
set ticslevel 0.8
set isosample 40,40

set view 60, 30, 1, 1
set contour base

splot "dataset" using 2:1:($3) notitle

Я пытаюсь провести некоторый анализ на этом графике, поэтому хотел получить этов Matlab, но я не уверен, как это нарисовать.Я попытался импортировать набор данных в Matlab, и вот как далеко я смог получить.Я загружаю файл и строю графики, используя следующие операторы Matlab:

load data
rangeY = floor(min(data(:,2))):.5:ceil(max(data(:,2)))
rangeX = floor(min(data(:,1))):.5:ceil(max(data(:,1)))
[X,Y] = meshgrid(rangeX,rangeY)
Z = griddata(data(:,1),data(:,2),data(:,3),X,Y, 'cubic')
surf(X,Y,Z)

enter image description here

Изображение выглядит для меня совершенно иначе (диапазон оси, форма и т. Д.) Может кто-нибудь сказать мнекак получить сюжет, похожий на тот, который я получил через Gnuplot?

Ответы [ 2 ]

3 голосов
/ 05 марта 2011

Причина, по которой surf не будет работать сразу, состоит в том, что данные довольно шумные, как вы увидите, если вы позвоните

plot3(data(:,1),data(:,2),data(:,3),'.')

Таким образом, вам сначала нужно сгладить данные (чтоЯ думаю, это то, что делает функция gnuplot).Ниже приведен один подход к сглаживанию данных

%# set bin edges (maybe you want to do 5:10:205)
xEdge = 10:10:200;
yEdge = xEdge;

%# bin the data
xId = sum(bsxfun(@ge,data(:,1),xEdge(2:end-1)),2)+1;
yId = sum(bsxfun(@ge,data(:,2),yEdge(2:end-1)),2)+1;

%# average z within every bin
smoothData = accumarray([xId,yId],data(:,3),[length(xCenter),length(yCenter)],@mean);

%# remove bins with no data
smoothData(smoothData==0) = NaN;

%# bin centers
xCenter = (xEdge(1:end-1)+xEdge(2:end))/2;
yCenter = xCenter;

%# plot
meshc(xCenter,yCenter,smoothData)

enter image description here

1 голос
/ 04 марта 2011

Я удивлен, что ваш код не работает.Я попробовал это на одном из моего набора данных, и это работало хорошо.В качестве первого ответа я бы предложил опубликовать ссылку на ваш набор данных (если она не является конфиденциальной) и попробовать другие методы интерполяции (начиная со значения по умолчанию linear).

ОднакоЯ заметил, что griddata произвел довольно много NaN на границах домена XY, хотя мой набор данных довольно плотный и хорошо распределен в этом домене.Я проверил документ и упомянуто, что:

Иногда griddata может возвращать точки в или рядом с выпуклой оболочкой данных в виде NaN.Это потому, что округление в вычислениях иногда затрудняет определение того, находится ли точка вблизи границы в выпуклой оболочке.

Я не думаю, что это является причиной вашей проблемы, но я все ещеподозреваю, что эта функция не очень хорошо работает с очень редкими наборами данных.Вместо этого вы должны попробовать TriScatteredInterp, что в любом случае быстрее.

...