如何对音频进行单元测试?


13

我已经继承了一个小项目,并希望通过为要添加的所有新代码编写单元测试来扩展并稳定它。第一类TypedAudioCreator创建音频文件,事实证明,这很容易首先进行测试,然后编写代码。

但是,到了编写的时间TypedAudioPlayer,我不知道该如何测试。这是一门很小的课程,专注于播放声音的基础知识:

public class TypedAudioFilePlayer
{
    public event StartedPlayingHandler StartedPlaying;
    public event StoppedPlayingHandler StoppedPlaying;

    public readonly int TimeBetweenPlays;

    private Queue<TypedAudioFile> _playlist = new Queue<TypedAudioFile>(); 

    public TypedAudioFilePlayer(int timeBetweenPlays)
    {
        TimeBetweenPlays = timeBetweenPlays;
    }

    public void AddFile(TypedAudioFile file)
    {
        _playlist.Enqueue(file);
    }

    public void StartPlaying()
    {
        ThreadPool.QueueUserWorkItem(ignoredState =>
        {
            while (_playlist.Count > 0)
            {
                var audioFile = _playlist.Dequeue();

                if (StartedPlaying != null)
                    StartedPlaying(audioFile);

                audioFile.SoundPlayer.PlaySync();
                audioFile.SoundPlayer.Dispose();

                if (StoppedPlaying != null)
                    StoppedPlaying(audioFile);
            }
        });
    }

    public void StopPlaying()
    {
        if (StoppedPlaying != null)
            StoppedPlaying(null);
    }
}

我在TDD上还很新,但是我意识到这种做法的好处,并且想尝试并做得更好。我先编写了代码,这里没有测试,但这只是我太懒了,无法正确地考虑TDD解决它的方式。我的问题是,我应该/应该如何测试这堂课?


2
C#中没有模拟框架吗?这应该可以解决您的问题。
user43552

2
@ user43552:那只是测试一个模拟游戏...这种情况下旨在测试音频播放器。
史蒂文·埃弗斯

5
我不熟悉如何使用C#进行音频处理,但在我看来,您需要重构此类,以便可以代替注入模拟audioFile.SoundPlayer。然后用这个模拟测试,验证PlaySync,并Dispose在适当的地方被调用。您还希望能够注入StartedPlayingHandler和,StoppedPlayingHandler如果可能的话。
达伍德说,请

2
这不应该在stackoverflow上吗?
Amr H. Abd Elmajeed

3
@ AmrH.AbdelMajeed-为什么呢?仅仅因为它有代码?
克里斯·

Answers:


10

在大多数系统中,有很多东西“边缘”无法充分进行单元测试。例如,任何产生图形或声音的东西。对于这类系统,最好进行手动测试。即使给出了自动化解决方案,这些输出也将为人类感知。知道您正在产生所需效果的唯一方法是让人类与他们互动。

可能可以执行手动测试,然后记录该手动测试的输出并创建一个自动测试以确保输出不变。请注意,尽管此类测试非常脆弱,但要注意:对基础代码的任何更改都可能需要重复手动测试,然后为自动测试创建新的记录。


1
+1表示“大多数系统“处于边缘”无法充分进行单元测试。”

2
这个答案很容易引起误解。仅仅因为音频代码的最终输出设备通常是一对扬声器,并不意味着音频代码无法进行单元测试或需要进行感知测试。所有音频软件均具有可测量的数字输出,并可与预期输出进行比较。在本文中
jb 2014年

9

自动测试音频播放器确实播放音频显然很困难,但是无论如何您都可以创建有用的单元测试。例如,您可以测试StartPlaying()引起StartedPlaying事件,而StopPlaying()引起StoppedPlaying事件。尝试播放空播放列表或空播放列表时,您可以测试行为。您可以测试AddFile是否确实将文件添加到播放列表中。您可以测试是否在播放音频文件后将其从播放列表中删除(如果需要)。也许有些破损的音频文件等也值得测试。

通过对这些事情进行单元测试,可以确保类表现良好,即符合合同规定。如果可以,但是仍然无法播放声音,则在手动测试中相对容易抓住。


3

请记住,单元测试(这是编写用于测试代码的各个单元的小型测试的行为)与运行单元测试的自动测试运行器(通常作为构建过程的一部分或某种连续性)之间的区别集成系统。

单元测试通常是自动化的,但仍可以手动执行。IEEE不赞成一个。单元测试的目的是隔离单元并验证其正确性。手动进行单元测试的方法可以使用分步指导文档。

http://en.wikipedia.org/wiki/Unit_testing#Techniques

您可以轻松编写单元测试来测试音频播放器组件是否正确播放音频:

  1. 确保扬声器在工作并且音量已调高。
  2. 转到/ my / test / folder。
  3. 执行myTestRunner audioPlayerTest.script.thingee。
  4. 您会听到贝多芬的第五交响曲演奏15秒钟。
  5. 如果您什么也听不到,则音频播放的时间超过或少于15秒,或者以任何方式失真,则测试失败。否则,测试通过。

您不容易做到的是将该测试包含在自动化测试系统中。自动化测试是单元测试的特定实现,但它不是唯一的实现。

另请参阅:https : //stackoverflow.com/questions/1877118/is-unit-testing-always-automated

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.