You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Arduino摇杆控制器坐标系旋转异常求助:指针使用是否有误?

问题分析与解决方案

没错,你的指针用法确实踩了C/C++里一个经典的坑,这就是导致输出始终为0,0的根本原因!

问题出在哪?

在你的rotate函数里,out是一个局部栈数组:

float out[] = { ... };
return out;

当函数执行完毕后,栈上的局部变量会被系统回收,返回的指针就变成了「悬空指针」——它指向的内存已经不属于你的程序了,读取这个地址的值是未定义行为(这里碰巧输出了0,0,换个环境可能会得到随机乱码或者直接崩溃)。

另外还要提一句:你调用rotate的时候少了个逗号!float(center) PI/2.0应该改成float(center), PI/2.0,不过这个语法错误编译器应该会报错,可能是你粘贴的时候漏了。

几种修复方案

方案1:使用静态数组(简单但要注意复用问题)

把out改成静态数组,这样它的内存会分配在全局区,函数结束后不会被释放:

float *rotate(float x, float y, float cx, float cy, float angle) {
    static float out[2]; // 静态数组,内存不会被回收
    out[0] = cx + (x - cx) * cos(angle) - (y - cy) * sin(angle);
    out[1] = cy + (x - cx) * sin(angle) + (y - cy) * cos(angle);
    return out;
}

⚠️ 注意:静态数组是全局共享的,如果你在多个地方同时调用rotate,会覆盖之前的结果,但Arduino是单线程程序,这个场景下没问题。

方案2:让调用者传入结果数组(更安全)

避免返回指针,而是让调用者提供一个数组来存储转换后的坐标:

void rotate(float x, float y, float cx, float cy, float angle, float *result) {
    result[0] = cx + (x - cx) * cos(angle) - (y - cy) * sin(angle);
    result[1] = cy + (x - cx) * sin(angle) + (y - cy) * cos(angle);
}

// 调用的时候这样写:
void loop() {
    int x = analogRead(X_pin);
    int y = analogRead(Y_pin);
    int center = 512;
    float transformed[2];
    rotate(float(x), float(y), float(center), float(center), PI/2.0, transformed);
    int tx = int(transformed[0]);
    int ty = int(transformed[1]);
    Serial.print(tx);
    Serial.print(",");
    Serial.println(ty); // 别忘了加换行,不然输出会挤在一起
}

方案3:用结构体返回结果(最清晰,推荐)

自定义一个结构体来存储坐标,这样代码可读性更高,也不用跟指针打交道:

// 定义坐标结构体
struct Point {
    float x;
    float y;
};

Point rotate(float x, float y, float cx, float cy, float angle) {
    Point p;
    p.x = cx + (x - cx) * cos(angle) - (y - cy) * sin(angle);
    p.y = cy + (x - cx) * sin(angle) + (y - cy) * cos(angle);
    return p;
}

// 调用的时候:
void loop() {
    int x = analogRead(X_pin);
    int y = analogRead(Y_pin);
    int center = 512;
    Point transformed = rotate(float(x), float(y), float(center), float(center), PI/2.0);
    int tx = int(transformed.x);
    int ty = int(transformed.y);
    Serial.print(tx);
    Serial.print(",");
    Serial.println(ty);
}

额外小建议

  • 别忘了在setup()里初始化串口:Serial.begin(9600);,不然可能看不到输出。
  • 如果你需要多次旋转不同角度,可以把角度变量提出来,方便调整。

内容的提问来源于stack exchange,提问作者Lorenzo Rivosecchi

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.14 07:37:30