Too complex for my small brain
Too complex for my small brain
Posted Nov 6, 2024 18:54 UTC (Wed) by NYKevin (subscriber, #129325)In reply to: Too complex for my small brain by khim
Parent article: Safety in an unsafe world
Definitions for people who don't Rust/C++:
* TMP: Template meta-programming, taking advantage of the C++ template system's overload resolution and backtracking to write arbitrarily complicated compile-time logic.
* Proc macros: Procedural macros, or macros that work by taking a stream of tokens, running it through some normal-ish Rust code at compile time, and feeding the result directly to the compiler.
* macro_rules!: Macros by example, or macro definitions that vaguely resemble C preprocessor macros (but with namespacing, greater flexibility, and stronger guardrails against doing things that don't make sense).
* Nested/recursive macro_rules!: Macro definitions that expand into calls to themselves and/or into additional macro definitions (which are subsequently used by the outer macro to do branching and the like). Usually involves the outer macro matching :tt and passing it along to the inner calls for further dissection.
Posted Nov 6, 2024 21:42 UTC (Wed)
by khim (subscriber, #9252)
[Link]
They are limited by the desire to get better diagnosis in the case of error. It's the same story as with statically typed language and dynamically typed languages: it's easier to write code in a dynamically typed languages but harder to debug it. Metaprogramming template language in C++ is dynamically typed with optional static annotations (close to python in spirit if not in syntax). Metaprogramming generics language in Rust is statically typed because of the best intentions: to make sure error messages would be readable. Unfortunately we all know where this road leads: error messages are kinda-sorta understandable if you can easily express what you need in an additive form, but if you couldn't… ho, boy that's where the fun begins. Thankfully when we are talking about keeping invariants unbroken you don't really need that machinery and can safely ignore it. Instead of working with types in Rust, you can just go and use constant verifiers (like in my example above). It's much easier to encode “business logic” in That's not a substitute for what one can do in C++ (because in C++ you can go back to types after working for a bit with constants), but it's more than enough to handle these “invariant verification” cases where you only need one of two ourcomes: code compiles (and, hopefully, works) or code doesn't compile (and you go and fix it). That's what tilted the decision for me: 99% of time I need complex metaprogramming simply to reject the bad code, not to actually play type tetris. Verification with
> Rust generics are limited, in my understanding, because they don't want people to start using TMP to do things that are better accomplished with proc macros
Too complex for my small brain
const
expressions because they don't need to be additive and you have plenty of normal logical operations there.const
is enough for that.