0

Java関数をjQueryと互換性を持たせる必要があります。jQuery Real Person キャプチャ検証関数は、Java によって記述されています。jQueryでキャプチャを検証したい。というわけで、jQueryでJava関数を書いてみました。しかし、関数は正しい値を返すことができませんでした。

ジャワ:

private String rpHash(String value) { 
   int hash = 5381; 
   value = value.toUpperCase(); 
   for(int i = 0; i < value.length(); i++) { 
     hash = ((hash << 5) + hash) + value.charAt(i); 
   } 
   return String.valueOf(hash); 
}

jQuery:

function rpHash(value) { 
  hash = 5381; 
  value = value.toUpperCase(); 
  for($i = 0; $i < value.length; $i++) { 
    hash = ((hash << 5) + hash) + value.charAt($i); 
  } 
  return hash; 
} 
4

1 に答える 1

3

期待される結果(Javaから)と実際の結果(JavaScriptから)を投稿すると便利です。文字列でテストしたところ"abc"、Java関数が返さ193450027れ、JavaScriptバージョンはが返されます"00177573ABC"。これらの結果を見ると、問題を見つけるのがはるかに簡単です。

問題は、ループ本体を正しく変換しなかったことです。hashint、したがって、((hash << 5) + hash)intです。ただし、value.charAt(i)ですchar。Javaがにを追加する必要がある場合はどうなりintますcharか?単純:acharは2バイトで表されるUnicode文字です。は同じUnicode値を持つにchar拡張されてから、に追加されます。intint

ただし、JavaScriptの動作は大きく異なります。hash はanumberで、value.charAt(i)string1文字です。にaを追加するnumberと、stringは2つのsの連結+として解釈されるため、結果も。になります。JavaScriptは静的に型付けされていないため、の値をからに変更することは完全に合法です。stringstringhashnumberstring

今後の反復でhashは、(ほとんどの場合)string数字と非数字の両方の文字を保持します。したがって、を評価するとき、シフト操作に必要なaから必要なへhash << 5の暗黙の変換はサイレントに失敗し、を返します。上記と同じ理由で、およびは連結になります。stringnumber0+ hash+ value.charAt($i)

したがって、正しい変換は、文字ではなく文字コードを取得することです。

hash = ((hash << 5) + hash) + value.charCodeAt($i);

これにより、意図した2つnumberの追加が正しく行われます。

無関係なことに、グローバルスコープへのリークを防ぐために、初期化var $i = 0の代わりに書き込みを行う必要があります。同じことが、にも当てはまります。これは、として宣言する必要があります。また、接頭辞が付いた変数はjQueryオブジェクトを表しますが、そうではありません。Javaのように名前を付ける方がよいでしょう。$i = 0$ihashvar hash = 5381$$ii

于 2013-01-31T11:23:47.677 に答える