c++ - 毕达哥拉斯恒等式 : how do I calculate the proper cos sign?

标签 c++ math trigonometry

有公式

cos(x) = sqrt(1-sin(x)^2)

我正在尝试在我的简单程序中对其进行测试,但我不知道我的错在哪里。 最终结果不正确。

#include <iostream>
#include <vector>
#include <cmath>

int main() {
    std::vector<float> data;

    constexpr float angleAdd = 360.0/10.0;
    constexpr float M_PI_DIVIDED_BY_180 = M_PI/180.0;

    for (auto angle = 0.0; angle < 360.0; angle += angleAdd) {
        data.push_back(angle);
    }

    //
    float res1 = 0;
    for (int i = 0; i < data.size(); ++i) {
        res1 += sin(data[i]*M_PI_DIVIDED_BY_180);
        res1 += cos(data[i]*M_PI_DIVIDED_BY_180);
    }

    std::cout << "\n\n";

    float res2 = 0;
    for (int i = 0; i < data.size(); ++i) {
        float angle = data[i];      
        float sinVal = sin(angle*M_PI_DIVIDED_BY_180);

        bool isPositiveSign = (angle >= 0 && angle <= 90) || (angle >= 270 && angle <= 360);
        float cosVal = sqrt(1 -sinVal*sinVal);
        if (isPositiveSign) {
            cosVal = fabs(cosVal);
        } else {
            cosVal = -1.0*fabs(cosVal);
        }

        res2 += sinVal;
        res2 += cosVal;
    }

    std::cout << "res1: " << res1 << " res2: " << res2 << std::endl;
    return 0;
}

它给了我:

res1: -6.89606e-07 res2: -3.57628e-07

显然,res2 是错误的。 我确定我对 cos 符号的计算有问题,但我无法弄清楚 - 是什么。 社区能否给我一些提示,这里出了什么问题?

最佳答案

您计算的数字为 res1res2将是零,如果你可以没有错误地进行计算。但是,浮点运算总是会出错。因此,您获得的两个不同结果只是浮点零对计算精度的两种不同表示形式——以 double 进行计算,您会发现幅度较小的结果。

另请注意 std::cos()std::sin()完全满足身份 square(sin)+square(cos)=1 .因此,

assert(square(std::cos(x)) != 1 - square(std::sin(x)));

对于 x 的大多数值(异常(exception)大概只有 0,也许只有 pi)。

res1res2都是零的近似值,它们的符号是任意的(尽管是确定性的)。如果您更改 angleAdd,您将得到不同的结果(但仍然与零的近似值一致)到 360 的另一个除数.

当然,所有这些都意味着您的程序不测试任何内容和 res1 的任何值。和 res2在几个std::numeric_limits<X>::epsilon()之内从零开始(其中 X 是使用的浮点类型)是有效的。没有正确的答案。

关于c++ - 毕达哥拉斯恒等式 : how do I calculate the proper cos sign?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/29489601/

相关文章:

c++ - Visual Studio 中带有 Autos 变量的锁定图标。它表示什么?

C++/WinRT : Can I await a single IAsyncAction handle from multiple coroutine calls?

c++ - 可以指定其基础的日志的 C++ 实现?

perl - 在 Perl 中将 1 添加到二进制字符串的最简单方法是什么?

c - x 和 y 的 atan2 输出为 0

function - LLVM 插入内在函数 Cos

c++ - 如何在 C++ 中以十六进制打印 '\n' 字符

c++ - 在 C 中转换为 unsigned char

c++ - 计算 ackermann 函数的较大值

math - 在二维空间中从 A 点到 B 点?