1: <?php declare(strict_types=1);
2:
3: namespace PhpParser\Node\Scalar;
4:
5: use PhpParser\Node\Scalar;
6:
7: class Float_ extends Scalar {
8: /** @var float Number value */
9: public float $value;
10:
11: /**
12: * Constructs a float number scalar node.
13: *
14: * @param float $value Value of the number
15: * @param array<string, mixed> $attributes Additional attributes
16: */
17: public function __construct(float $value, array $attributes = []) {
18: $this->attributes = $attributes;
19: $this->value = $value;
20: }
21:
22: public function getSubNodeNames(): array {
23: return ['value'];
24: }
25:
26: /**
27: * @param mixed[] $attributes
28: */
29: public static function fromString(string $str, array $attributes = []): Float_ {
30: $attributes['rawValue'] = $str;
31: $float = self::parse($str);
32:
33: return new Float_($float, $attributes);
34: }
35:
36: /**
37: * @internal
38: *
39: * Parses a DNUMBER token like PHP would.
40: *
41: * @param string $str A string number
42: *
43: * @return float The parsed number
44: */
45: public static function parse(string $str): float {
46: $str = str_replace('_', '', $str);
47:
48: // Check whether this is one of the special integer notations.
49: if ('0' === $str[0]) {
50: // hex
51: if ('x' === $str[1] || 'X' === $str[1]) {
52: // PHP 8.6 warns when hexdec() produces a float.
53: return @hexdec($str);
54: }
55:
56: // bin
57: if ('b' === $str[1] || 'B' === $str[1]) {
58: // PHP 8.6 warns when bindec() produces a float.
59: return @bindec($str);
60: }
61:
62: // oct, but only if the string does not contain any of '.eE'.
63: if (false === strpbrk($str, '.eE')) {
64: // substr($str, 0, strcspn($str, '89')) cuts the string at the first invalid digit
65: // (8 or 9) so that only the digits before that are used.
66: // PHP 8.6 warns when octdec() produces a float.
67: return @octdec(substr($str, 0, strcspn($str, '89')));
68: }
69: }
70:
71: // dec
72: return (float) $str;
73: }
74:
75: public function getType(): string {
76: return 'Scalar_Float';
77: }
78: }
79:
80: // @deprecated compatibility alias
81: class_alias(Float_::class, DNumber::class);
82: