【问题标题】:Sine wave generation using phase使用相位生成正弦波
【发布时间】:2016-07-10 19:35:12
【问题描述】:

我正在使用以下方法生成正弦波 -

sampling rate = 22050;
theta = 0;

for (i = 0; i < N; i++)  
{  
 theta = phase * 2 * PI;  
 signal[i] = amplitude * sin(theta);  
 phase = phase + frequency/sampling rate;  
}

当我生成频率为 8000 Hz 的信号时,输出会出现失真。低于此的频率(例如 6000 Hz)会正确生成。如果我像这样检查相位,则正确生成 8000 Hz 信号 -

if (phase > 1)  
{  
  float temp = phase - 1;  
  phase = temp;  
}  

我认为它与Xcode中的正弦函数有关,可能是它可以接受的值范围?相同的代码有和没有相位环绕在 Matlab 中没有区别。有人可以解释这里发生了什么吗?

【问题讨论】:

  • 如果你对 XCode 感兴趣,你需要告诉我们不同的变量是什么类型。这可能会显示一些东西。事实上,我只能看到temp的类型。
  • 嗨彼得,PI 被声明为双精度数,而 theta 在浮点数中。我将 theta 更改为 double,代码生成 8K 信号而不会失真。谢谢!
  • 很高兴听到。不过,我将把这个问题作为离题结束,并将其迁移到 SO。

标签: audio sampling phase nyquist


【解决方案1】:

@cixelsyd 有正确的公式......这是根据采样率创建一组给定频率的样本的代码

incr_theta := (2.0 * math.Pi * given_freq) / samples_per_second

phase := -1.74   // given phase ... typically 0 note its a constant
theta := 0.0

for curr_sample := 0; curr_sample < number_of_samples; curr_sample++ {

    source_buffer[curr_sample] = math.Sin(theta + phase)

    theta += incr_theta
}

为了提高效率,最好将 delta theta 的计算移到循环之外......注意阶段是一个常数,因为它只是给我们一个初始偏移量

【讨论】:

    【解决方案2】:

    我不确定,但我认为问题可能是:

    theta = phase * 2 * PI;  
    

    我认为 Xcode 会将结果更改为整数。您可能想尝试:

    theta = phase * 2.0 * PI;  
    

    请确保您的 PI 变量是 double

    所有这些都使 DSP.SE 偏离了主题。 :-)

    【讨论】:

      【解决方案3】:

      我认为计算应该是 (2.0 * PI) * 频率/采样率

      这将为您提供下一阶段的弧度增量。然后可以将该值输入到 Sin 函数中以计算相位。请注意,您需要累积弧度值。

      从技术上讲,您的第一个陈述是不正确的,因为它的措辞。 FS/2 是奈奎斯特值。您可以产生高于此的频率,但它们会混叠。

      就相位缠绕而言,有不同的方法来管理它。

      我对弧度的理解是,它是相位的“线性”表示,在相位围绕 2 pi 值旋转时不会重复。因此,如果您通过管理弧度来管理相位,您可能不会遇到换行问题。

      很高兴得到更多知识渊博的人的纠正。

      【讨论】:

        猜你喜欢
        • 2015-02-01
        • 2012-07-11
        • 1970-01-01
        • 2016-02-21
        • 2018-06-11
        • 1970-01-01
        • 1970-01-01
        • 2021-09-08
        相关资源
        最近更新 更多