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

如何在指定时长内实现数值递减至目标值?

C++实现指定时长内数值线性递减的方案

问题分析

你原代码的核心问题在于:试图一次性获取递减过程的结果并赋值给int变量,但数值递减是随时间变化的过程,无法通过单次调用直接得到最终值(除非阻塞程序直到完成,但这几乎没有实用价值)。

实用解决方案:非阻塞式实时获取当前值

这种方案适合游戏、UI动画等需要实时更新数值的场景,每次调用都能获取当前时间对应的递减数值。

方式1:使用类封装状态

#include <chrono>
#include <cmath>
#include <thread>
#include <cstdio>

class Decrementer {
private:
    int start_val;
    int end_val;
    std::chrono::seconds total_duration;
    std::chrono::steady_clock::time_point start_time;

public:
    Decrementer(int start, int end, int total_seconds)
        : start_val(start), end_val(end), total_duration(total_seconds), start_time(std::chrono::steady_clock::now()) {}

    int get_current() {
        const auto now = std::chrono::steady_clock::now();
        const auto elapsed = std::chrono::duration_cast<std::chrono::milliseconds>(now - start_time);
        
        // 计算进度,确保不超过100%
        const double progress = std::min(
            static_cast<double>(elapsed.count()) / (total_duration.count() * 1000.0),
            1.0
        );

        // 线性插值计算当前值
        int current = start_val + static_cast<int>((end_val - start_val) * progress);

        // 防止因浮点计算误差导致数值超出目标范围
        if (end_val < start_val) {
            return std::max(current, end_val);
        } else {
            return std::min(current, end_val);
        }
    }
};

// 使用示例
int main() {
    Decrementer dec(2000, 0, 40);
    
    // 模拟每秒获取一次当前值
    for (int i = 0; i < 45; ++i) {
        const int cool_variable = dec.get_current();
        printf("第%d秒:当前值 = %d\n", i, cool_variable);
        std::this_thread::sleep_for(std::chrono::seconds(1));
    }
    return 0;
}

方式2:使用带状态的lambda

如果偏好函数式风格,可以通过工厂函数返回一个捕获状态的lambda,每次调用lambda获取当前值:

#include <chrono>
#include <cmath>
#include <functional>
#include <thread>
#include <cstdio>

std::function<int()> make_decrementer(int start_val, int end_val, int total_seconds) {
    const auto start_time = std::chrono::steady_clock::now();
    const std::chrono::seconds total_duration(total_seconds);

    return [=]() {
        const auto now = std::chrono::steady_clock::now();
        const auto elapsed = std::chrono::duration_cast<std::chrono::milliseconds>(now - start_time);
        
        const double progress = std::min(
            static_cast<double>(elapsed.count()) / (total_duration.count() * 1000.0),
            1.0
        );

        int current = start_val + static_cast<int>((end_val - start_val) * progress);
        if (end_val < start_val) {
            return std::max(current, end_val);
        } else {
            return std::min(current, end_val);
        }
    };
}

// 使用示例
int main() {
    auto decrement = make_decrementer(2000, 0, 40);
    
    for (int i = 0; i < 45; ++i) {
        const int cool_variable = decrement();
        printf("第%d秒:当前值 = %d\n", i, cool_variable);
        std::this_thread::sleep_for(std::chrono::seconds(1));
    }
    return 0;
}

阻塞式方案(仅作参考,实用性低)

如果必须阻塞程序直到数值递减完成,可以用以下代码,但会导致程序暂停指定时长:

#include <chrono>
#include <thread>

int decrement_blocking(int start_val, int end_val, int total_seconds) {
    std::this_thread::sleep_for(std::chrono::seconds(total_seconds));
    return end_val;
}

// 使用示例(会阻塞40秒)
int main() {
    int cool_variable = decrement_blocking(2000, 0, 40);
    return cool_variable;
}

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.14 13:20:35