acosf() 返回 NaN [英] acosf() returns NaN

查看:94
本文介绍了acosf() 返回 NaN的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个用 Objective C 编写的 iPhone 应用程序,我正在收集用户在屏幕上绘制的触摸点以创建路径.

I have a iPhone application written in Objective C where I'm collecting the touch points the user draws on to the screen to create a path.

我希望能够精简这些数据.我旨在通过检查点的角度是否超过某个阈值来实现此目的的方法之一.例如,如果我取 a、b、c 线上的任意三个相邻点,如果角度 ABC 在 180 度的 5 度以内,那么我可以删除 b 点,而不会对这条线产生太大影响.

I want to be able to thin this data. One of the ways I'm aiming to do this by checking if the angle of a point is over a certain threshold. For instance, if I take any three adjacent points on the line called a,b,c, if the angle ABC is within 5 degrees of 180, then I could remove point b without affecting the line too much.

我试图通过将三角形 ABC 分成 2 个直角三角形来实现这一点.然后我使用 acosf() 找到 a (BAC) 处的角度和 c (BCA) 处的角度.然后我可以从 180 中减去这两个角度来找到 ABC 的角度.

I'm trying to achieve this by splitting the triangle ABC into 2 right-angled triangles. I'm then using acosf() to find the angle at a (BAC) and the angle at c (BCA). I can then subtract both these angles from 180 to find the angle of ABC.

我的问题是 acosf() 经常返回 NaN.当它返回一个数字时,我已经在计算器上检查过它的值是正确的.我试过返回 NaN 的值,但它们也不适用于计算器.我知道这是因为它们超出了 acosf() 的范围.我怎样才能避免这种情况?

My issue is that acosf() is often returning NaN. When it returns a number I've checked it on a calculator and the value is correct. I've tried the values that return NaN and they don't work on a calculator either. I know that this is because they are out of range for acosf(). How Can I avoid this?

这是我正在使用的代码:

Here is the code I'm using:

float prevToNextDist = ccpDistance(prevPoint.location, nextPoint.location);
    //work out the next point angle
    float pointToNextDistance = ccpDistance(point.location, nextPoint.location);
    float nextPointAngle = acosf((prevToNextDist/2)/pointToNextDistance);
    nextPointAngle = CC_RADIANS_TO_DEGREES(nextPointAngle);

    //work out the previous point angle
    float prevToPointDistance = ccpDistance(prevPoint.location, point.location);
    float prevPointAngle = acosf((prevToNextDist/2)/prevToPointDistance);
    prevPointAngle = CC_RADIANS_TO_DEGREES(prevPointAngle);

    //work out the point angle
    float pointAngle = 180 - nextPointAngle - prevPointAngle;

有什么想法吗?

推荐答案

好的,我已经解决了这个问题,所以我将我的解决方案发布给任何可能偶然发现这个步骤并发现它有用的人.虽然,我使用的是我自己的解决方案,但 chux 和 AProgrammers 的建议都是合理的,并帮助我提出了解决方案,所以我对他们都投了赞成票.

Ok, I've worked this out, so I'm posting my solution for anybody who might stumble across this tread and find it useful. Although, I'm using using my own solution, both chux and AProgrammers's advice is sound, and helped me come up with the solution, so I've upvoted them both.

正如 chux 所建议的,atan2() 是比 acosf() 更好用的函数.这是基于角度的细化点数据的代码:

As chux suggested, atan2() is the better function to use rather than acosf(). Here's the code that thin's the points data based on angle:

#define kAngleTolerance 3

    double prevPointAngle = atan2(point.location.y - prevPoint.location.y, point.location.x - prevPoint.location.x) * 180.0f / M_PI;
    prevPointAngle = fabs(prevPointAngle);

    double nextPointAngle = atan2(nextPoint.location.y - point.location.y, nextPoint.location.x - point.location.x) * 180.0f / M_PI;
    nextPointAngle = fabs(nextPointAngle);

    double pointAngle = 180 - fabs(nextPointAngle - prevPointAngle);

    if (pointAngle < 180 + kAngleTolerance && pointAngle > 180 - kAngleTolerance ) {
        point.remove = YES;
        [pointsToRemove addObject:point];
    }

这篇关于acosf() 返回 NaN的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆