Skip to main content

reifydb_engine/expression/arith/
mod.rs

1// SPDX-License-Identifier: AGPL-3.0-or-later
2// Copyright (c) 2025 ReifyDB
3
4/// Generates a complete match expression dispatching all numeric type pairs to the appropriate
5/// handler functions. Uses push-down accumulation to build the cross-product of type arms.
6///
7/// Fixed-width pairs (12×12=144 arms) use `$fh`, while any pair involving arbitrary-precision
8/// types (81 arms) uses `$ah`. Additional match arms are appended via `$($extra:tt)*`.
9macro_rules! dispatch_arith {
10	// Entry point
11	(
12		$left:expr, $right:expr;
13		fixed: $fh:ident, arb: $ah:ident ($ctx:expr, $target:expr, $fragment:expr);
14		$($extra:tt)*
15	) => {
16		dispatch_arith!(@rows
17			($left, $right) $fh $ah ($ctx, $target, $fragment)
18			[Float4 Float8 Int1 Int2 Int4 Int8 Int16 Uint1 Uint2 Uint4 Uint8 Uint16]
19			{$($extra)*}
20			{}
21		)
22	};
23
24	// Recursive: process one fixed-left type, generating all 15 right-side arms
25	(@rows
26		($left:expr, $right:expr) $fh:ident $ah:ident ($ctx:expr, $target:expr, $fragment:expr)
27		[$L:ident $($rest:ident)*]
28		{$($extra:tt)*}
29		{$($acc:tt)*}
30	) => {
31		dispatch_arith!(@rows
32			($left, $right) $fh $ah ($ctx, $target, $fragment)
33			[$($rest)*]
34			{$($extra)*}
35			{
36				$($acc)*
37				(ColumnData::$L(l), ColumnData::Float4(r)) => $fh($ctx, l, r, $target, $fragment),
38				(ColumnData::$L(l), ColumnData::Float8(r)) => $fh($ctx, l, r, $target, $fragment),
39				(ColumnData::$L(l), ColumnData::Int1(r)) => $fh($ctx, l, r, $target, $fragment),
40				(ColumnData::$L(l), ColumnData::Int2(r)) => $fh($ctx, l, r, $target, $fragment),
41				(ColumnData::$L(l), ColumnData::Int4(r)) => $fh($ctx, l, r, $target, $fragment),
42				(ColumnData::$L(l), ColumnData::Int8(r)) => $fh($ctx, l, r, $target, $fragment),
43				(ColumnData::$L(l), ColumnData::Int16(r)) => $fh($ctx, l, r, $target, $fragment),
44				(ColumnData::$L(l), ColumnData::Uint1(r)) => $fh($ctx, l, r, $target, $fragment),
45				(ColumnData::$L(l), ColumnData::Uint2(r)) => $fh($ctx, l, r, $target, $fragment),
46				(ColumnData::$L(l), ColumnData::Uint4(r)) => $fh($ctx, l, r, $target, $fragment),
47				(ColumnData::$L(l), ColumnData::Uint8(r)) => $fh($ctx, l, r, $target, $fragment),
48				(ColumnData::$L(l), ColumnData::Uint16(r)) => $fh($ctx, l, r, $target, $fragment),
49				(ColumnData::$L(l), ColumnData::Int { container: r, .. }) => $ah($ctx, l, r, $target, $fragment),
50				(ColumnData::$L(l), ColumnData::Uint { container: r, .. }) => $ah($ctx, l, r, $target, $fragment),
51				(ColumnData::$L(l), ColumnData::Decimal { container: r, .. }) => $ah($ctx, l, r, $target, $fragment),
52			}
53		)
54	};
55
56	// Base case: all fixed-left types processed, emit the match with arb-left arms
57	(@rows
58		($left:expr, $right:expr) $fh:ident $ah:ident ($ctx:expr, $target:expr, $fragment:expr)
59		[]
60		{$($extra:tt)*}
61		{$($acc:tt)*}
62	) => {
63		match ($left, $right) {
64			// Fixed × Fixed + Fixed × Arb (12 × 15 = 180 arms)
65			$($acc)*
66
67			// Arb × all (3 × 15 = 45 arms)
68			(ColumnData::Int { container: l, .. }, ColumnData::Float4(r)) => $ah($ctx, l, r, $target, $fragment),
69			(ColumnData::Int { container: l, .. }, ColumnData::Float8(r)) => $ah($ctx, l, r, $target, $fragment),
70			(ColumnData::Int { container: l, .. }, ColumnData::Int1(r)) => $ah($ctx, l, r, $target, $fragment),
71			(ColumnData::Int { container: l, .. }, ColumnData::Int2(r)) => $ah($ctx, l, r, $target, $fragment),
72			(ColumnData::Int { container: l, .. }, ColumnData::Int4(r)) => $ah($ctx, l, r, $target, $fragment),
73			(ColumnData::Int { container: l, .. }, ColumnData::Int8(r)) => $ah($ctx, l, r, $target, $fragment),
74			(ColumnData::Int { container: l, .. }, ColumnData::Int16(r)) => $ah($ctx, l, r, $target, $fragment),
75			(ColumnData::Int { container: l, .. }, ColumnData::Uint1(r)) => $ah($ctx, l, r, $target, $fragment),
76			(ColumnData::Int { container: l, .. }, ColumnData::Uint2(r)) => $ah($ctx, l, r, $target, $fragment),
77			(ColumnData::Int { container: l, .. }, ColumnData::Uint4(r)) => $ah($ctx, l, r, $target, $fragment),
78			(ColumnData::Int { container: l, .. }, ColumnData::Uint8(r)) => $ah($ctx, l, r, $target, $fragment),
79			(ColumnData::Int { container: l, .. }, ColumnData::Uint16(r)) => $ah($ctx, l, r, $target, $fragment),
80			(ColumnData::Int { container: l, .. }, ColumnData::Int { container: r, .. }) => $ah($ctx, l, r, $target, $fragment),
81			(ColumnData::Int { container: l, .. }, ColumnData::Uint { container: r, .. }) => $ah($ctx, l, r, $target, $fragment),
82			(ColumnData::Int { container: l, .. }, ColumnData::Decimal { container: r, .. }) => $ah($ctx, l, r, $target, $fragment),
83
84			(ColumnData::Uint { container: l, .. }, ColumnData::Float4(r)) => $ah($ctx, l, r, $target, $fragment),
85			(ColumnData::Uint { container: l, .. }, ColumnData::Float8(r)) => $ah($ctx, l, r, $target, $fragment),
86			(ColumnData::Uint { container: l, .. }, ColumnData::Int1(r)) => $ah($ctx, l, r, $target, $fragment),
87			(ColumnData::Uint { container: l, .. }, ColumnData::Int2(r)) => $ah($ctx, l, r, $target, $fragment),
88			(ColumnData::Uint { container: l, .. }, ColumnData::Int4(r)) => $ah($ctx, l, r, $target, $fragment),
89			(ColumnData::Uint { container: l, .. }, ColumnData::Int8(r)) => $ah($ctx, l, r, $target, $fragment),
90			(ColumnData::Uint { container: l, .. }, ColumnData::Int16(r)) => $ah($ctx, l, r, $target, $fragment),
91			(ColumnData::Uint { container: l, .. }, ColumnData::Uint1(r)) => $ah($ctx, l, r, $target, $fragment),
92			(ColumnData::Uint { container: l, .. }, ColumnData::Uint2(r)) => $ah($ctx, l, r, $target, $fragment),
93			(ColumnData::Uint { container: l, .. }, ColumnData::Uint4(r)) => $ah($ctx, l, r, $target, $fragment),
94			(ColumnData::Uint { container: l, .. }, ColumnData::Uint8(r)) => $ah($ctx, l, r, $target, $fragment),
95			(ColumnData::Uint { container: l, .. }, ColumnData::Uint16(r)) => $ah($ctx, l, r, $target, $fragment),
96			(ColumnData::Uint { container: l, .. }, ColumnData::Int { container: r, .. }) => $ah($ctx, l, r, $target, $fragment),
97			(ColumnData::Uint { container: l, .. }, ColumnData::Uint { container: r, .. }) => $ah($ctx, l, r, $target, $fragment),
98			(ColumnData::Uint { container: l, .. }, ColumnData::Decimal { container: r, .. }) => $ah($ctx, l, r, $target, $fragment),
99
100			(ColumnData::Decimal { container: l, .. }, ColumnData::Float4(r)) => $ah($ctx, l, r, $target, $fragment),
101			(ColumnData::Decimal { container: l, .. }, ColumnData::Float8(r)) => $ah($ctx, l, r, $target, $fragment),
102			(ColumnData::Decimal { container: l, .. }, ColumnData::Int1(r)) => $ah($ctx, l, r, $target, $fragment),
103			(ColumnData::Decimal { container: l, .. }, ColumnData::Int2(r)) => $ah($ctx, l, r, $target, $fragment),
104			(ColumnData::Decimal { container: l, .. }, ColumnData::Int4(r)) => $ah($ctx, l, r, $target, $fragment),
105			(ColumnData::Decimal { container: l, .. }, ColumnData::Int8(r)) => $ah($ctx, l, r, $target, $fragment),
106			(ColumnData::Decimal { container: l, .. }, ColumnData::Int16(r)) => $ah($ctx, l, r, $target, $fragment),
107			(ColumnData::Decimal { container: l, .. }, ColumnData::Uint1(r)) => $ah($ctx, l, r, $target, $fragment),
108			(ColumnData::Decimal { container: l, .. }, ColumnData::Uint2(r)) => $ah($ctx, l, r, $target, $fragment),
109			(ColumnData::Decimal { container: l, .. }, ColumnData::Uint4(r)) => $ah($ctx, l, r, $target, $fragment),
110			(ColumnData::Decimal { container: l, .. }, ColumnData::Uint8(r)) => $ah($ctx, l, r, $target, $fragment),
111			(ColumnData::Decimal { container: l, .. }, ColumnData::Uint16(r)) => $ah($ctx, l, r, $target, $fragment),
112			(ColumnData::Decimal { container: l, .. }, ColumnData::Int { container: r, .. }) => $ah($ctx, l, r, $target, $fragment),
113			(ColumnData::Decimal { container: l, .. }, ColumnData::Uint { container: r, .. }) => $ah($ctx, l, r, $target, $fragment),
114			(ColumnData::Decimal { container: l, .. }, ColumnData::Decimal { container: r, .. }) => $ah($ctx, l, r, $target, $fragment),
115
116			// Additional arms (special cases, undefined handling, error fallback)
117			$($extra)*
118		}
119	};
120}
121
122pub mod add;
123pub mod div;
124pub mod mul;
125pub mod rem;
126pub mod sub;