Warning: file_get_contents(/data/phpspider/zhask/data//catemap/0/amazon-s3/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C#:数字的通用接口_C#_Generics - Fatal编程技术网

C#:数字的通用接口

C#:数字的通用接口,c#,generics,C#,Generics,我正在尝试执行一些与数字类型无关的通用数字操作。然而,我知道没有办法使用泛型来实现这一点。第一个想法是使用where语句过滤传入的类型,但是所有的数字类型都是封闭的,因此对于泛型过滤器无效。此外,泛型不允许标准的数字操作(加法、移位等),因此我能想到的唯一解决方案是非泛型地重新编写每个方法。还有其他想法吗 以下是我最初尝试的代码,仅供参考: private const int BYTE_SIZE = 8; private const int UINT16_SIZE = 16;

我正在尝试执行一些与数字类型无关的通用数字操作。然而,我知道没有办法使用泛型来实现这一点。第一个想法是使用where语句过滤传入的类型,但是所有的数字类型都是封闭的,因此对于泛型过滤器无效。此外,泛型不允许标准的数字操作(加法、移位等),因此我能想到的唯一解决方案是非泛型地重新编写每个方法。还有其他想法吗

以下是我最初尝试的代码,仅供参考:

    private const int BYTE_SIZE = 8;

    private const int UINT16_SIZE = 16;

    private const int UINT32_SIZE = 32;

    private const int UINT64_SIZE = 64;

    public static byte[] ToBytes(UInt16[] pnaValues)
    {
        return ToSmaller<byte, UInt16>(pnaValues, BYTE_SIZE, UINT16_SIZE);
    }

    public static byte[] ToBytes(UInt32[] pnaValues)
    {
        return ToSmaller<byte, UInt32>(pnaValues, BYTE_SIZE, UINT32_SIZE);
    }

    ....

    public static UInt16[] ToUInt16s(byte[] pnaValues)
    {
        return ToLarger<UInt16, byte>(pnaValues, UINT16_SIZE, BYTE_SIZE);
    }

    public static UInt16[] ToUInt16s(UInt32[] pnaValues)
    {
        return ToSmaller<UInt16, UInt32>(pnaValues, UINT16_SIZE, UINT32_SIZE);
    }

    ...

    public static UInt64[] ToUInt64s(UInt32[] pnaValues)
    {
        return ToLarger<UInt64, UInt32>(pnaValues, UINT64_SIZE, UINT32_SIZE);
    }

    private static TLarger[] ToLarger<TLarger, TSmaller>(TSmaller[] pnaSmaller, int pnLargerSize, int pnSmallerSize)
        where TLarger : byte, UInt16, UInt32, UInt64
        where TSmaller : byte, UInt16, UInt32, UInt64
    {
        TLarger[] lnaRetVal = null;
        int lnSmallerPerLarger = pnLargerSize / pnSmallerSize;

        System.Diagnostics.Debug.Assert((pnLargerSize % pnSmallerSize) == 0);

        if (pnaSmaller != null)
        {
            System.Diagnostics.Debug.Assert((pnaSmaller % lnSmallerPerLarger) == 0);

            lnaRetVal = new TLarger[pnaSmaller.Length / lnSmallerPerLarger];

            for (int i = 0; i < lnaRetVal.Length; i++)
            {
                lnaRetVal[i] = 0;

                for (int j = 0; j < lnSmallerPerLarger; j++)
                {
                    lnaRetVal[i] = (lnaRetVal[i] << pnLargerSize) + pnaSmaller[i * lnSmallerPerLarger + j];
                }
            }
        }

        return lnaRetVal;
    }

    private static TSmaller[] ToSmaller<TSmaller, TLarger>(TLarger[] pnaLarger, int pnSmallerSize, int pnLargerSize)
        where TSmaller : byte, UInt16, UInt32, UInt64
        where TLarger : byte, UInt16, UInt32, UInt64
    {
        TSmaller[] lnaRetVal = null;
        int lnSmallerPerLarger = pnLargerSize / pnSmallerSize;

        System.Diagnostics.Debug.Assert((pnLargerSize % pnSmallerSize) == 0);

        if (pnaSmaller != null)
        {
            lnaRetVal = new TSmaller[pnaLarger.Length * lnSmallerPerLarger];

            for (int i = 0; i < lnaRetVal.Length; i++)
            {
                for (int j = 0; j < lnSmallerPerLarger; j++)
                {
                    lnaRetVal[i * lnSmallerPerLarger + (lnSmallerPerLarger - 1 - j)]
                        = pnaLarger[i] >> (j * pnLargerSize);
                }
            }
        }

        return lnaRetVal;
    }
private const int BYTE_SIZE=8;
私有const int UINT16_SIZE=16;
私人建筑内部UINT32_尺寸=32;
私有常量int UINT64_SIZE=64;
公共静态字节[]个字节(UInt16[]个字节)
{
返回到maller(pAvalue、字节大小、UINT16大小);
}
公共静态字节[]个字节(UInt32[]个字节)
{
返回到maller(pnavalue、字节大小、UINT32大小);
}
....
公共静态UInt16[]ToUInt16s(字节[]pnaValues)
{
返回到大器(pnaValues、UINT16\u大小、字节大小);
}
公共静态UInt16[]ToUInt16s(UInt32[]pAvalues)
{
返回到小型机(pnaValues、UINT16_尺寸、UINT32_尺寸);
}
...
公共静态UInt64[]ToUInt64s(UInt32[]pAvalues)
{
返回至放大器(pnaValues、UINT64_尺寸、UINT32_尺寸);
}
专用静态TLarger[]ToLarger(TSmaller[]pnaSmaller,int-pnLargerSize,int-pnSmallerSize)
式中:字节,UInt16,UInt32,UInt64
其中TSmaller:byte,UInt16,UInt32,UInt64
{
TLarger[]lnaRetVal=null;
int lnsmallerparger=pnLargerSize/pnSmallerSize;
System.Diagnostics.Debug.Assert((pnLargerSize%pnSmallerSize)==0);
if(pnaSmaller!=null)
{
System.Diagnostics.Debug.Assert((pnaSmaller%lnsmallerlarger)==0);
lnaRetVal=新的标签[pnaSmaller.Length/lnsmaller-larger];
对于(int i=0;i(j*pnLargerSize);
}
}
}
返回lnaRetVal;
}

对于由数字类型实现的算术运算,没有通用接口。这可能有助于解决您的问题。

重写可能是最简单的。我唯一能想到的解决方案是超越模板,编写一个表示函数的字符串,为类型指定占位符,然后用每种类型替换它命名并在运行时编译它


除了由于编译导致的初始性能下降外,调用这些函数也很困难。

特别是在这种情况下,
操作符.Convert(TFrom value)
可能会很有用。请注意,我没有实现
左移
右移
,但添加它们很简单。移植
eval()
to C#?见鬼,不