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

如何用C++计算卧式圆柱储罐液体体积?ESP32计算偏差求助

卧式圆柱储罐液体体积计算问题排查与修正

原代码的核心问题

  1. 公式完全错误:你写的式子既不是正确的弓形面积,也没乘以储罐长度length——卧式圆柱的体积是液体横截面积(弓形面积)× 储罐长度,原代码连最基础的体积计算逻辑都缺失。
  2. 圆周率精度不足:用3.14代替π会引入不必要的计算误差,应该用标准数学库的M_PI常量。
  3. 缺少输入校验:没考虑height的合法范围(必须在0到2*radius之间,也就是0到储罐直径),传感器异常值会导致计算崩溃或结果异常。

正确的计算逻辑

卧式圆柱的液体横截面积是弓形面积,分两种情况计算:

  • 当液体高度height ≤ radius(半罐以下):
    弓形面积 = 扇形面积 - 三角形面积
    公式:radius² × acos((radius - height)/radius) - (radius - height) × sqrt(2×radius×height - height²)
  • 当液体高度height > radius(半罐以上):
    弓形面积 = 圆面积 - 空出部分的弓形面积
    公式:M_PI×radius² - [radius² × acos((height - radius)/radius) - (height - radius) × sqrt(2×radius×height - height²)]

最终体积 = 弓形面积 × 储罐长度length

修正后的代码

#include <math.h> // 必须包含math.h才能使用M_PI、acos、sqrt

double radius = 100;
double height = 50; // 传感器读取的水深,单位cm
double length = 450; // 储罐长度,单位cm
double volume; // 最终体积,单位cm³(1L=1000cm³)

void calculateVolume() {
    // 输入合法性校验
    if (height < 0) {
        volume = 0;
        return;
    }
    if (height >= 2 * radius) {
        volume = M_PI * radius * radius * length;
        return;
    }

    double segmentArea;
    if (height <= radius) {
        segmentArea = (radius * radius) * acos((radius - height)/radius) - (radius - height) * sqrt(2 * radius * height - height * height);
    } else {
        double emptyHeight = 2 * radius - height;
        segmentArea = M_PI * radius * radius - [(radius * radius) * acos((radius - emptyHeight)/radius) - (radius - emptyHeight) * sqrt(2 * radius * emptyHeight - emptyHeight * emptyHeight)];
    }

    volume = segmentArea * length;
}

注意事项

  • ESP32编译时要确保开启数学库支持(默认开启),如果遇到M_PI未定义的问题,可在#include <math.h>前添加#define _USE_MATH_DEFINES。
  • 传感器读取的height建议做滤波处理,避免数据波动导致计算值跳变。
  • 最终体积单位是立方厘米,转换成升只需除以1000。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.18 08:31:04