C# CSPRN的子字符串也是CSPRN吗?

C# CSPRN的子字符串也是CSPRN吗?,c#,string,random,cryptography,C#,String,Random,Cryptography,我想生成一个4个字符长的CSPRN(加密安全的Psuedo随机数)字符串。我知道我可以通过创建一个5字节长的随机数组并将其编码为base32来创建一个8字符的数组: string CSPRN = ""; System.Security.Cryptography.RandomNumberGenerator rng = new System.Security.Cryptography.RNGCryptoServiceProvider(); byte[] tokenData = new byte[5]

我想生成一个4个字符长的CSPRN(加密安全的Psuedo随机数)字符串。我知道我可以通过创建一个5字节长的随机数组并将其编码为base32来创建一个8字符的数组:

string CSPRN = "";
System.Security.Cryptography.RandomNumberGenerator rng = new System.Security.Cryptography.RNGCryptoServiceProvider();
byte[] tokenData = new byte[5];
rng.GetBytes(tokenData);
CSPRN = Base32.ToBase32String(tokenData);  //should produce a string 5bytes*1.6charsperbyte = 8 chars long.
如果我现在取CSPRN前4个字符的子字符串,它仍然是CSPRN吗


我的猜测是肯定的,但我想知道是否有任何“陷阱”来自于获取一个子串而不是生成一个较小的数字。

是的,是的。首先让我们看一下您的第一个安全声明。Base32是一种5位编码,因此,如果生成5次任何内容(比如一个字节),则生成的字符串包含每个字符的完整熵


当然,如果你把每个字符的熵从字符串中去掉,它不会突然下降。因此,如果你选择4个字符,每个字符都应该包含完整的熵,在32个基本字母表中只给你4个完整的熵字符。

有趣的是,我在网上上了由Dan Boneh教授的Coursera课程(我高度推荐),其中包括这个主题。是的,CSPRN输出的任何部分都是加密安全的。即使是单个比特,随机性也无法与掷硬币区分开来。如果它甚至在那个级别上都不安全,那么就不可能从那个系统构建一个加密安全的更大输出。考虑到许多流密码依赖于这个属性,即使在比特级也是随机的。我对你的答案有点迷惑-是的,每个字符的熵对于所有子串都是相同的,但是这本身并不能证明任何东西,每个字符只代表RNG中的5位。只要是这样,你基本上不必担心。这是更好的描述吗?你也可以在crypto网站上询问专家的意见,尽管我在那里也是前十名:P