xref: /plugin/combo/vendor/antlr/antlr4-php-runtime/src/Comparison/Hasher.php (revision 37748cd8654635afbeca80942126742f0f4cc346)
1*37748cd8SNickeau<?php
2*37748cd8SNickeau
3*37748cd8SNickeaudeclare(strict_types=1);
4*37748cd8SNickeau
5*37748cd8SNickeaunamespace Antlr\Antlr4\Runtime\Comparison;
6*37748cd8SNickeau
7*37748cd8SNickeaufinal class Hasher
8*37748cd8SNickeau{
9*37748cd8SNickeau    private function __construct()
10*37748cd8SNickeau    {
11*37748cd8SNickeau    }
12*37748cd8SNickeau
13*37748cd8SNickeau    public static function hash(...$values) : int
14*37748cd8SNickeau    {
15*37748cd8SNickeau        return self::hashArray($values);
16*37748cd8SNickeau    }
17*37748cd8SNickeau
18*37748cd8SNickeau    /**
19*37748cd8SNickeau     * @param array<mixed> $values
20*37748cd8SNickeau     */
21*37748cd8SNickeau    private static function hashArray(array $values) : int
22*37748cd8SNickeau    {
23*37748cd8SNickeau        $result = 1;
24*37748cd8SNickeau        foreach ($values as $value) {
25*37748cd8SNickeau            $elementHash = self::hashValue($value);
26*37748cd8SNickeau            $result = (31 * $result + $elementHash) & 0xffffffff;
27*37748cd8SNickeau        }
28*37748cd8SNickeau
29*37748cd8SNickeau        return $result;
30*37748cd8SNickeau    }
31*37748cd8SNickeau
32*37748cd8SNickeau    public static function hashValue($value) : int
33*37748cd8SNickeau    {
34*37748cd8SNickeau        if ($value === null) {
35*37748cd8SNickeau            return 0;
36*37748cd8SNickeau        }
37*37748cd8SNickeau
38*37748cd8SNickeau        if (\is_int($value)) {
39*37748cd8SNickeau            return $value;
40*37748cd8SNickeau        }
41*37748cd8SNickeau
42*37748cd8SNickeau        if ($value instanceof Hashable) {
43*37748cd8SNickeau            return $value->hashCode();
44*37748cd8SNickeau        }
45*37748cd8SNickeau
46*37748cd8SNickeau        if (\is_object($value)) {
47*37748cd8SNickeau            return \spl_object_id($value);
48*37748cd8SNickeau        }
49*37748cd8SNickeau
50*37748cd8SNickeau        if (\is_array($value)) {
51*37748cd8SNickeau            return self::hashArray($value);
52*37748cd8SNickeau        }
53*37748cd8SNickeau
54*37748cd8SNickeau        if (\is_bool($value) || \is_float($value) || \is_resource($value)) {
55*37748cd8SNickeau            return (int) $value;
56*37748cd8SNickeau        }
57*37748cd8SNickeau
58*37748cd8SNickeau        return \crc32((string) $value);
59*37748cd8SNickeau    }
60*37748cd8SNickeau}
61