matlab中怎样从曲线中获得精确的坐标值~~~~~~~~~~~~~~

matlab中怎样从曲线中获得精确的坐标值~~~~~~~~~~~~~~,第1张

提供几种不同的做法,供参考。

方法1:

=====

直接从绘图数据插值(经检验z数据是单调增加的),代码如下:

syms x y z

eq1=-2pi00541500000002sin(x)sin((5pi/6)+x)-4/3pi 

    00000002^32000z98+2/3piz9800000002^3 

    (1820-1000)(cos(x))^3-2/3piz9800000002^3 

    (1820+1000)-piz9800000002^2(y+00000002cos(x)) 

    (1820-1000)(sin(x))^2; 

eq2=-sin((5pi/6)+x)besselk(0,(z98(1820-1000)/005415)^ 

    0500000002sin(x))+(z98(1820-1000)/005415)^05 

    ybesselk(1,(z98(1820-1000)/005415)^0500000002sin(x));

Z=solve(eq1,z);

eq=subs(eq2,z,Z);

h=ezplot(eq,[052 05245],[-1e-9 0]);

X=get(h,'XData');

Y=get(h,'YData');

view(-10,35)

grid on

zz=subs(Z,{x y},{X Y});

X(zz>20000)=[];

Y(zz>20000)=[];

zz(zz>20000)=[];

set(h, 'XData', X, 'YData', Y, 'ZData', zz, 'linewidth', 2);

title('')

zlabel('z')

axis tight

box off

zi = [1 10 100 1000 5000 10000 19000 20000];

xi = interp1(zz, X, zi, 's');

yi = interp1(zz, Y, zi, 's');

vpa([xi; yi]',10)

举例:

------

上面的代码中z分别取[1 10 100 1000 5000 10000 19000 20000],得到的结果如下(每行代表一组对应的x、y):

[      5235988072,  1770687259e-12]

[      5235990919, -3682753278e-13]

[      5236019385, -2134703182e-11]

[      5236304028, -2157265249e-10]

[      5237568792, -9522223488e-10]

[      5239149030,  -1794854554e-9]

[      5241991463,  -3217413726e-9]

[      5242307131,  -3370566367e-9]

把数据代回方程,看一下精度:

>> eq = subs([eq1; eq2], {x y z}, {xi yi zi})

eq =

  10e-005 

    00000   -00000   -00000   -00000    00000   -00000   -00000   -00000

    02096    02519    03885    00182    00055    00072    00034   -00010

>> norm(eq)

ans =

  50868e-006

说明:

------

(1)你所贴代码的前半部分本来用于说明两个曲面相交的,如果只画线,该部分属于多余;

(2)顺便修正一点小错误——原代码的这两句有点小问题

x(z>20000)=NaN;

y(z>20000)=NaN;

我上次还有点奇怪,为什么坐标范围看上去不太对劲,但没有深究。刚才发现是这两句写错了,x、y应该是大写的。另外,现在为符合插值的需要应把右侧NaN改为空矩阵([])。

(3)有多种插值方法可用,我使用了最有利于平滑曲线的样条插值,楼主也可以试试其它做法。

(4)注意z0取值的范围最好不要超过[min(z) max(z)]=[845 19943],如果超出该范围,部分方法需要通过参数指定允许interp1外插(默认情况下,样条插值允许外插,但线性插值不允许)。

(5)由于方法本身是基于部分离散点信息得到未知点的,所以很难说是否能保证精度。

(6)兼容性:这里的绘图代码在2007b上测试没问题,但在65上不行,更高版本没试,也可能会有问题。

方法2:

=====

从原始问题出发,直接解方程,代码如下:

syms x y z

eq1=-2pi00541500000002sin(x)sin((5pi/6)+x)-4/3pi 

    00000002^32000z98+2/3piz9800000002^3 

    (1820-1000)(cos(x))^3-2/3piz9800000002^3 

    (1820+1000)-piz9800000002^2(y+00000002cos(x)) 

    (1820-1000)(sin(x))^2; 

eq2=-sin((5pi/6)+x)besselk(0,(z98(1820-1000)/005415)^ 

    0500000002sin(x))+(z98(1820-1000)/005415)^05 

    ybesselk(1,(z98(1820-1000)/005415)^0500000002sin(x));

zi = [1 10 100 1000 5000 10000 19000 20000];

xi = sym( zi0 );

yi = xi;

for i = 1 : length(zi)

    z0 = zi(i);

    [xi(i), yi(i)] = solve(subs(eq1,z,z0), subs(eq2,z,z0));

end

vpa([xi-2pi; yi]',10)

举例:

------

与方法1 的测试用例相同,得到的结果如下:

[       523598806, -3251499235e-13]

[       523599091, -2887359289e-12]

[       523601938, -2523219710e-11]

[       523630402, -2159081181e-10]

[       523756878, -9522774887e-10]

[       523914902,  -1794926954e-9]

[       524199145,  -3217447875e-9]

[       524230712,  -3370556700e-9]

同样,检验一下精度:

>> eq = subs([eq1; eq2], {x y z}, {xi-2pi yi zi});

>> eq=double(eq)

eq =

  10e-018 

    00000    00000    00000    00000    00000    00000    00000    00000

    00000    00002    00021    00182    00812    01539    02774    02907

>> norm(eq)

ans =

  43823e-019

说明:

------

(1)由于求解方程组得到x总是位于要求的坐标范围之外,所以把它减小2pi。

(2)这种方法需要符号数学工具箱的支持,精度远高于前一种方法。

(3)兼容性:用solve解方程的结果可能和符号数学工具箱版本相关,我用Maple内核的65和2007b做了测试,可以求出想要的结果,但在MuPad内核的版本上可能会有问题。

方法3:

=====

使用数值方法解方程。本来以为第2种方法有些条件下会失效,所以考虑这种做法,但从实际情况看,方法2的效果很好,所以,这个就不做了。

====================================

最后,八卦几句:

已经多次回答楼主的问题了,有点好奇您是从哪里找到这么多复杂的表达式要求解的,和您的工作有关吗?而且难得的是,问题看上去虽然比较复杂,但根据楼主提供的信息,刚好都是可以求解的,简直就像是考试的试题一般。

顺便说一下,我注意到,这次的方程与上次我回答的问题相比,有7处由978换成了98(想来应该是重力加速度),应该是有意为之的吧?

有多种显示的方式,比如使用fprintf()或者disp()

个人喜欢用fprintf(),输出可以更人性化一些

比如:

y = [1 3 2 4 7 9 10 2 3];

t = [2 3 6 10 12 17 18 22 24];

Mean_y = mean(y);

Var_y = var(y);

fprintf('Mean_y=%f, Var_y=%f\n', Mean_y, Var_y); % 按照格式化文本设定打印

disp(Mean_y); % 直接打印Mean_y的值

由ginput定义就知道,它只能获取二维坐标。不能获取三维坐标。

ginput提供了一个十字光标使我们能更精确的选择我们所需要的位置,并返回坐标值。函数调用形式为:

[x,y] = ginput(n)

[x,y] = ginput

[x,y,button] = ginput()

对于[x,y] = ginput(n),能使你从当前的坐标系中读取n个点,并返回这n个点的x,y坐标,均为nX1的向量。可以按回车提前结束读数。

[x,y] = ginput 可以无限的读取坐标直到按下回车键。

方法:

要获取三维坐标系。打开用图形里面的tools——Data curser

如下图:

1)把这张读取到一个矩阵中,a=imread('路径')

2)分析,显然找这样一个点:它是红色的,并且它上下左右都是红色的点。因此我们可以规定,如果某一个点是红色的,并且改点上,下,左,右方的5个像素单位(这个数字可以根据图去预估)也是红的,那么就是中心点

3)在矩阵a中每一个像素挨个检查(实际是从第五行第五列开始检查),它和它周围四个点,与[1,0,0](红色)相差不大(不大的程度可以用一个数值来描述,比如0001等等),则认为找到了。找到后输出相应的横纵下标,就是中心点相对位置。

4)难点就在于找什么样的特征来描述中心点,尽可能做到不重不漏;找什么样的特征在于自己。

以上就是关于matlab中怎样从曲线中获得精确的坐标值~~~~~~~~~~~~~~全部的内容,包括:matlab中怎样从曲线中获得精确的坐标值~~~~~~~~~~~~~~、Matlab怎么可以读取点的坐标、matlab ginput问题 三维坐标系里怎么用ginput获取坐标;等相关内容解答,如果想了解更多相关内容,可以关注我们,你们的支持是我们更新的动力!

欢迎分享,转载请注明来源:内存溢出

原文地址:https://54852.com/web/9288915.html

(0)
打赏 微信扫一扫微信扫一扫 支付宝扫一扫支付宝扫一扫
上一篇 2023-04-26
下一篇2023-04-26

发表评论

登录后才能评论

评论列表(0条)

    保存