这 10 行比较字符串相等的代码给我整懵了,不信你也来看看


抱歉用这种标题吸引你点进来了,不过你不妨看完,看看能否让你有所收获。
先直接上代码:
boolean?safeEqual(String?a,?String?b)?{
???if?(a.length()?!=?b.length())?{
???????return?false;
???}
???int?equal?=?0;
???for?(int?i?=?0;?i?<?a.length();?i++)?{
???????equal?|=?a.charAt(i)?^?b.charAt(i);
???}
???return?equal?==?0;
}
上面的代码是我根据原版(Scala)翻译成?Java的,Scala?版本(最开始吸引程序猿石头注意力的代码)如下:
def?safeEqual(a:?String,?b:?String)?=?{
??if?(a.length?!=?b.length)?{
????false
??}?else?{
????var?equal?=?0
????for?(i?<-?Array.range(0,?a.length))?{
??????equal?|=?a(i)?^?b(i)
????}
????equal?==?0
??}
}
刚开始看到这段源码感觉挺奇怪的,这个函数的功能是比较两个字符串是否相等,首先“长度不等结果肯定不等,立即返回”这个很好理解。
再看看后面的,稍微动下脑筋,转弯下也能明白这其中的门道:通过异或操作1^1=0, 1^0=1, 0^0=0,来比较每一位,如果每一位都相等的话,两个字符串肯定相等,最后存储累计异或值的变量equal必定为 0,否则为 1。
再想一下呢?
for?(i?<-?Array.range(0,?a.length))?{
??if?(a(i)?^?b(i)?!=?0)?//?or?a(i)?!=?b[i]
????return?false
}
我们常常讲性能优化,从效率角度上讲,难道不是应该只要中途发现某一位的结果不同了(即为1)就可以立即返回两个字符串不相等了吗?(如上所示)。
这其中肯定有……
再细想一下呢?
结合方法名称?safeEquals?可能知道些眉目,与安全有关。
以前知道通过延迟计算等手段来提高效率的手段,但这种已经算出结果却延迟返回的,还是头一回!
我们来看看,JDK 中也有类似的方法,如下代码摘自?java.security.MessageDigest:
public?static?boolean?isEqual(byte[]?digesta,?byte[]?digestb)?{
???if?(digesta?==?digestb)?return?true;
???if?(digesta?==?null?||?digestb?==?null)?{
???????return?false;
???}
???if?(digesta.length?!=?digestb.length)?{
???????return?false;
???}
???int?result?=?0;
???//?time-constant?comparison
???for?(int?i?=?0;?i?<?digesta.length;?i++)?{
???????result?|=?digesta[i]?^?digestb[i];
???}
???return?result?==?0;
}
看注释知道了,目的是为了用常量时间复杂度进行比较。
但这个计算过程耗费的时间不是常量有啥风险?(脑海里响起了背景音乐:“小朋友,你是否有很多问号?”)
safeEquals("abcdefghijklmn", "xbcdefghijklmn")?(只有首位不相同)和调用?safeEquals("abcdefghijklmn", "abcdefghijklmn")?(两个完全相同的字符串)的所耗费的时间一样。防止通过大量的改变输入并通过统计运行时间来暴力破解出要比较的字符串。关注公众号:拾黑(shiheibook)了解更多
[广告]赞助链接:
四季很好,只要有你,文娱排行榜:https://www.yaopaiming.com/
让资讯触达的更精准有趣:https://www.0xu.cn/
关注网络尖刀微信公众号随时掌握互联网精彩
- 1 习近平将发表二〇二六年新年贺词 7904141
- 2 2026年国补政策来了 7808738
- 3 东部战区:开火!开火!全部命中! 7712893
- 4 2026年这些民生政策将惠及百姓 7616985
- 5 小学食堂米线过期2.5小时被罚5万 7519709
- 6 解放军喊话驱离台军 原声曝光 7428214
- 7 为博流量直播踩烈士陵墓?绝不姑息 7327605
- 8 每月最高800元!多地发放养老消费券 7238391
- 9 数字人民币升级 1月1日起将计付利息 7141831
- 10 2026年1月1日起 一批新规将施行 7040675








CSDN
