2008-09-26 118 views
186

什么是可以在.NET中创建的最长的字符串?就我所知,String类的文档没有提到这个问题,因此权威答案可能需要一些内部知识。在64位系统上的最大变化是什么?.NET字符串的最大可能长度是多少?

[这要求更多的好奇心比实际使用 - !我不打算创建一个使用巨大字符串的任何代码]

回答

270

理论极限可能是2,147,483,647,但实际极限远不及此。由于.Net程序中没有单个对象可能超过2GB,并且字符串类型使用unicode(每个字符2字节),所以您可以做的最好的是1,073,741,823,但是您不可能分配到32位机器。

这是那些"If you have to ask, you're probably doing something wrong."

47

由于System.String的长度属性是一个Int32,我猜想那最大长度将是2,147,483,647个字符(最大Int32大小)。如果它允许更长时间,你将无法检查长度,因为这会失败。

+10

+1好扣除 – 2011-03-11 11:10:51

+2

@ m.edmondson:实际上我并不确信。一个[array](https://msdn.microsoft.com/en-us/library/system.array%28v=vs.110%29.aspx)实例也有一个LongLength,一个流使用`long `作为长度。虽然它是有效的答案,但它没有一个准确的方法来衡量这一点。 – 2015-01-27 19:59:05

+0

但是前两位用于ASCII /非ASCII指示,因为[这篇文章](https://www.codeproject.com/Articles/3377/Strings-UNDOCUMENTED)说,所以它应该是2^30 = 1 073 741 824 – Saito 2017-02-10 12:04:53

0

由于string.length减为整数(这是一个的Int32别名)它的大小被限制为Int32.MaxValue Unicode字符;)

60

基于我的高度科学准确实验中,顶出我的机器上远远早于10亿个字符(我仍在运行下面的代码以获得更好的精确定位)。 更新:几个小时后,我放弃了。最终结果:可能会超过100,000,000个字符,立即给出System.OutOfMemoryException为1,000,000,000个字符。

using System; 
using System.Collections.Generic; 

public class MyClass 
{ 
    public static void Main() 
    { 
     int i = 100000000; 
     try 
     { 
      for (i = i; i <= int.MaxValue; i+= 5000) 
      { 
       string value = new string('x', i); 
       //WL(i); 
      } 
     } 
     catch (Exception exc) 
     { 
      WL(i); 
      WL(exc); 
     } 
     WL(i); 
     RL(); 
    } 

    #region Helper methods 

    private static void WL(object text, params object[] args) 
    { 
     Console.WriteLine(text.ToString(), args); 
    } 

    private static void RL() 
    { 
     Console.ReadLine(); 
    } 

    private static void Break() 
    { 
     System.Diagnostics.Debugger.Break(); 
    } 

    #endregion 
} 
+25

在这里应用二进制搜索可能会帮助您更快地找到答案... – Mario 2010-07-12 21:08:58

+24

使用测试驱动的答案。 – 2011-01-04 00:46:03

1

200兆......此时你的应用研到虚拟停顿情形之一的,大约有演出工作集内存和O/S开始像你将需要重新启动。

static void Main(string[] args) 
{ 
    string s = "hello world"; 
    for(;;) 
    { 
     s = s + s.Substring(0, s.Length/10); 
     Console.WriteLine(s.Length); 
    } 
} 

12 
13 
14 
15 
16 
17 
18 
... 
158905664 
174796230 
192275853 
211503438 
20

对于任何人来到这个话题晚了,我看得出来,hitscan的“你可能不应该这样做”可能导致有人要问,他们应该做些什么?

StringBuilder类是常一个简单的替换。 如果您的数据来自文件,请考虑stream-based classes之一。

s = s +“stuff”的问题在于它必须分配一个全新的区域来保存数据,然后将所有旧数据复制到它并加上新的东西 - 每个和每个循环ITERATION。因此,用s = s +“stuff”加上5个字节到100万是极其昂贵的。 如果你想要的只是写5个字节到最后并继续你的程序,那么你必须选择一个课程,留下一些增长空间。

StringBuilder sb = new StringBuilder(5000); 
for (; ;) 
    { 
     sb.Append("stuff"); 
    } 

StringBuilder将auto-grow by doubling当它的限制被击中。所以你会在开始时看到一次增长的痛苦,一次是5000字节,再次是10000,再次是20000.附加字符串会在每次循环迭代时产生痛苦。

5

字符串不是由整数限定,通常认为

存储器限制之外,字符串不能有多于2 (1,073,741,824)字符,因为一个2GB的限制是由微软的CLR(通用语言强加运行)。

希望这可能在未来发生变化。

0

请注意,BinaryWriter.Write(字符串)将字符串长度写为无符号字符(一个字节)!

相关问题