2010-07-24 8 views
0

je suis en train de mettre en œuvre DataOutputStream en php (DataOutputStream du langage java) dans le code java, ils changent les variables droite comme celui-ci >>>changement PHP droite

en php je ne peux changer comme ça >>

comment puis-je faire cela en PHP?

merci

Répondre

4

Vous pouvez implement the behavior of the unsigned right shift operator >>> with the signed shift operators comme ceci:

La valeur de n>>>s est ns positions de bit décalé à droite avec zéro extension. Si n est positif, le résultat est le même que celui de n>>s; si n est négatif, le résultat est égal à celui de l'expression (n>>s)+(2<<~s) si le type de l'opérande gauche est int, et à la suite de l'expression (n>>s)+(2L<<~s) si le type de l'opérande gauche est longue . Le terme ajouté (2<<~s) ou (2L<<~s) annule le bit de signe propagé.

+1

donc ce que je dois faire fonction privée shiftRight3 ($ a, $ b) { si (is_n umeric ($ a) && $ a <0) { return $ a >> $ b + (2 << ~ $ b); } else { return $ a >> $ b; } } – shay

+1

@shay: Oui, exactement. – Gumbo

+0

merci à tous :) – shay

0

En forme masquée pour toute plate-forme (32 bits, 64 bits ... l'avenir aussi longtemps que PHP_INT_MAX est définie) qui peut offrir un avantage de performance (pas de branchement):

function uintRShift($uint,$shift) 
{ 
    //if ($shift===0) return $uint; 
    //PHP_INT_MAX on 32 =7FFFFFFF, or zero & 32 ones 
    $mask=PHP_INT_MAX>>($shift-1); 
    return $uint>>$shift&$mask; 
} 

La puts configuration du masque tous les zéros pour les $shift bits les plus à gauche de $uint. Note: Décommenter la première ligne si vous voulez pouvoir/tolérer le décalage d'un nombre négatif/grand (puisque le masque modifiera un nombre négatif/grand même avec $shift=0).

Le code de test unitaire pour montrer qu'il fonctionne en 32 bits:

class UintRShiftTest extends PHPUnit_Framework_TestCase { 
    public function provide_shifts() { 
     return array(
     /* start   shift  end*/ 
      array(0,   4,   0) 
     ,array(0xf,  4,   0) 
     ,array(0xff,  4,   0xf) 
     ,array(0xfffffff, 4,   0xffffff) 
     ,array(0xffffffff, 4,   0xfffffff) 
     ,array(-1,   4,   0xfffffff)//Same as above 
     ,array(0,   1,   0) 
     ,array(0xf,  1,   0x7) 
     ,array(-1,   1,   0x7fffffff) 
     ); 
    } 

    /** 
    * @dataProvider provide_shifts 
    */ 
    function test_uintRShift($start,$shift,$end) { 
     $this->assertEquals($end,uintRShift($start,$shift)); 
    } 
} 

Pour ce que ça vaut la fonction mentionnée ci-dessus:

function uintRShift_branch($uint,$shift) 
{ 
    if ($uint<0) { 
     return ($uint>>$shift)+(2<<~$shift); 
    } else { 
     return $uint>>$shift; 
    } 
} 

ne réussit pas le test automatisé:

  • # 4 Rapports -1.Cela peut peut-être justifiée par PHP rapports 0xffffffff comme un grand nombre positif (documentation suggère de grands entiers sont automagiquement passés à flotteurs, bien que le décalage de bits semble le traiter comme un entier régulier encore)

  • # 8 Résultats en -2147483649 qui est en fait correcte (comme 0x7fffffff) mais au-dessous de la valeur int minimum pour PHP: -2147483648