【问题标题】:How do I cast a variable to the same type of a dynamic variable?如何将变量转换为相同类型的动态变量?
【发布时间】:2014-07-27 22:30:33
【问题描述】:

我目前正在研究一种将 PCM 样本作为ICollection<dynamic> 接受的放大方法(调用者只会传递以下任一集合:sbyteshortint)。我创建的放大算法运行良好;只是我不确定如何将新放大的样本转换回其原始类型,因为放大逻辑将样本输出为List<double>

我知道我可以添加某种switch 语句来将样本转换回它们的原始类型,但这似乎是一个相当原始的解决方案,有没有更好的方法来完成这个?

我如何调用该方法(samplesList<dynamic> 延续 ints,file 是我为读取 wav 文件创建的类),

AmplifyPCM(samples, file.BitDepth, 0.5f);

我的方法,

static private List<dynamic> AmplifyPCM(ICollection<dynamic> samples, ushort bitDepth, float volumePercent)
{
    var highestSample = 0;
    var temp = new List<dynamic>();

    foreach (var sample in samples)
    {
        if (sample < 0)
        {
            temp.Add(-sample);
        }
        else
        {
            temp.Add(sample);
        }
    }

    foreach (var sample in temp)
    {
        if (sample > highestSample)
        {
            highestSample = sample;
        }
    }

    temp = null;

    var ratio = (volumePercent * (Math.Pow(2, bitDepth) / 2)) / highestSample; 
    var newSamples = new List<dynamic>();

    foreach (var sample in samples)
    {
        newSamples.Add(sample * ratio); // ratio is of type double, therefore implicit conversion from whatever sample's type is to a double.
    }

    // switch statement would go here if there's no better way.

    return newSamples;
}

【问题讨论】:

  • 你可以让这个方法通用,不是吗?
  • @ToughCoder 我没想过使用泛型,是的,我想这可以解决问题。谢谢。你想写一个答案,这样我就可以给你荣誉了吗?
  • 很高兴为您提供帮助。感谢您的信任。

标签: c# .net variables dynamic casting


【解决方案1】:

好吧,您可以将其设为通用的,以提供返回类型。但是 C# 不支持具有泛型的运算符。您可以尝试将它们转换为动态的。

static private List<T> AmplifyPCM<T>(ICollection<T> samples, ushort bitDepth, float volumePercent)
{
    var highestSample = 0;
    var temp = new List<T>();

    foreach (var sample in samples)
    {
        if ((dynamic)sample < 0)
        {
            temp.Add(-(dynamic)sample);
        }
        else
        {
            temp.Add(sample);
        }
    }

    foreach (var sample in temp)
    {
        if ((dynamic)sample > highestSample)
        {
            highestSample = (dynamic)sample;
        }
    }

    temp = null;

    var ratio = (volumePercent * (Math.Pow(2, bitDepth) / 2)) / highestSample;
    var newSamples = new List<T>();

    foreach (var sample in samples)
    {
        newSamples.Add((dynamic)(T)sample * ratio);
    }

    return newSamples;
}

【讨论】:

  • 你不能对 T 进行算术运算。 sample &lt; 0-sample 之类的东西不会编译。也没有办法说,例如where T : number 允许这样的事情,这可能是该方法以 `dynamic 开头的原因。
  • @TimS。我没有检查 Visual Studio 上的代码。让我检查一下,我会更新我的答案。
  • 啊,是的,我刚刚检查过了,我认为我没有使用泛型是有原因的,不过感谢您的建议。
  • 有趣,我没想过将两者结合起来。
  • @Sam 你可以创建 IArithmetic 接口来转换 int、double 类型,但它太麻烦了。检查此 Jon Skeet 的通用运算符链接:yoda.arachsys.com/csharp/miscutil/usage/genericoperators.html
猜你喜欢
  • 2012-12-22
  • 1970-01-01
  • 1970-01-01
  • 2020-06-18
  • 2011-01-28
  • 2014-07-02
  • 2020-06-19
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多