将int转换为char的最快方法是什么?

7
什么是将int转换为char的最快方法? 我需要更快的方法,因为,
convertingchar = Convert.ToChar(intvalue);

这是我程序中最慢的部分。我有多个不同的整数值,需要转换为字符。

我的项目非常大,无法发布我的函数。这就是为什么我发布这个测试函数的原因。

char convertingchar = ' ';
...some code...
public void convert(int intvalue){
   convertingchar = Convert.ToChar(intvalue);
}

3
你是如何进行个人资料分析的? - JustSomeGuy
5
Convert.ToChar 最终会执行显式转换,如 (char)value,其中 value 是你的 int 值。在这样做之前,它会检查确保 value 在范围 0 到 0xffff 内,并在不是时引发 OverflowException。额外的方法调用、值/边界检查和 OverflowException 可能是有用的,但如果不需要,直接使用 (char)value 的性能会更好。 - Mahesh
1
我认为我需要比那更快的方法,因为在Visual Studio中进行性能测试后,这是我最慢的部分。请记住这只是一个测试函数。我只是想知道是否有更快的转换方式。 - user4628051
1
@CyberDude 记住这只是我的测试函数,实际项目中的函数更加复杂。我只是想提取出我的问题。 - user4628051
3
如果这是你程序中最耗时的部分,你可能需要找到一种不逐个转换每个字符或减少转换次数的方法。 - Emond
显示剩余8条评论
3个回答

20

通过运行快速性能测试来比较你的Convert.ToChar方法和提到的强制转换方法,我发现执行了65535个测试(char.MaxValue):

Convert: 00:00:00.0005447 total
Cast:    00:00:00.0003663 total

在最佳情况下,转换时的性能大约是转型的一半。

参考来源中发现的Convert.ToChar的实现揭示了它的耗时:

public static char ToChar(int value) {
    if (value < 0 || value > Char.MaxValue) throw new OverflowException(Environment.GetResourceString("Overflow_Char"));
    Contract.EndContractBlock();
    return (char)value;
}

虽然这些检查确实有一定的作用,但在您特定的用例,尤其是在如此关键的性能情况下,可能不需要它们。这取决于您。

一个很好的替代方法是使用ushort而不是int来强制执行这些检查。显然,这可能可行也可能不可行,但是具有相同的最大值,这意味着您将获得编译时检查,以替代之前依赖ToChar执行的功能。


3
在这里,ushort的作用不可低估——它将使任何边界检查变得无关紧要,从而让您获得速度和准确性。 - Trenin
3
@Trenin-虽然你所说的是正确的,但是为了向函数提供ushort而采取的任何努力,都比创建intushort更好地创建一个char,然后完全不调用char ToChar(char)函数。换句话说,如果他有int并且无法更改,则应保留原状。如果可以更改,则应更改为char而不是ushort - rolfl

17

Convert.ToChar 最终会执行显式转换,如 (char)value, 其中 value 是你的 int 值。在执行转换之前,它会检查确保 value 在范围 0 到 0xffff 内,并且如果不是,则抛出 OverflowException 异常。附加的方法调用、值/边界检查和 OverflowException 可能很有用,但如果不需要,只使用 (char)value 就会更快。

这样做可以保证转换过程顺利进行,但在确保过程中可能会花费一些时间。

convertingchar = Convert.ToChar(intvalue);

这将进行转换,而无需确保一切正常,因此用时更少。

convertingchar = (char)intvalue;

例如。

 Console.WriteLine("(char)122 is {0}", (char)122);
产生的结果为:

(char)122是z


注意

虽然不直接与问题有关,但如果您觉得转换速度较慢,那么您可能做错了什么。问题是为什么需要将许多int转换为char。您想要实现什么目标。可能会有更好的方法。


我现在正在使用你的代码,它运行良好且比我之前的解决方案更快。 - user4628051
(char)value 不进行范围检查吗? - Random832

8

与其他人注意到的相反,最快的方法是根本不运行任何代码。在所有其他情况下,都为int分配了内存,并为char分配了内存。因此,能够实现的最佳方法只是将int复制到char地址。

然而,由于根本没有运行代码,因此这段代码的速度快100%。

[StructLayout(LayoutKind.Explicit)]
public struct Foo
{
    [FieldOffset(0)] 
    public int Integer;
    [FieldOffset(0)] 
    public char Char;
}

https://msdn.microsoft.com/en-us/library/aa288471%28v=vs.71%29.aspx


你现在如何能够转换? - user4628051
将一个整数移动到整数字段中,并从字符字段中获取字符。 - Lasse V. Karlsen
@LasseVKarlsen 是的,您需要编写代码将值移动到整数中。在这种情况下,您不会获得任何好处。但是,如果将字段集成到读取或写入值的对象中,则可以跳过单个副本... - Aron
3
你的代码不具备可移植性,因为其效果取决于字节序(除非C#以某种方式统一字节序,但这至少是不太可能的),并且不应该对优化性能产生任何影响(除非优化真的很糟糕)。 - Frax
@Frax 这个问题是关于纯性能的。否则我会同意。 - Aron
显示剩余8条评论

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接