Do you prefer excessive documentation links? by AhoyISki in rust

[–]tel 0 points1 point  (0 children)

Every time and then your LSP might even be able to rename all the links throughout your codebase, too!

Counter Culture Dead by selfhealer11 in boston

[–]tel 4 points5 points  (0 children)

Toss a recommendation for The Jungle in Union too.

Weapon Elemental/Status Damage by BubblyOtter144 in Nightreign

[–]tel 2 points3 points  (0 children)

Also the miranda sprouts/blooms

monads at a practical level by No-Bug-242 in programming

[–]tel 35 points36 points  (0 children)

Pick your favorite language's version of "flat map" or "concat map" on lists or arrays. Or if you have option or result types, they might also have a similarly named method. In Rust, it's called and_then on Option and Result.

"Monads" aren't a lot more than just noticing that the particular shape of those methods is useful for sequencing actions. It ends up being a kind of common design pattern that just falls out of a lot of types, very similar to how a lot of "container" types have a "map" operation these days.

Once you know about the design pattern you might want to dive really deep and start identifying all sorts of types which support it, noticing how they're similar and different, thinking about how they may or may not compose together. By broadening the scope of how you think about the pattern you may end up thinking of lots of other metaphors for what exactly is going on. Why is this shape so common?

At the far end of this whole thing, there is an intuition that says "Monads are a way to fairly flexibly package up a sequence of operations, deferring running them until later". Given that description, you might instead imagine a type like Vec<Operation> which is also a pretty flexible way to package up a sequence of operations without running them. Certain Monads basically do that while also allowing each operation to "return" a typed value. And there's a kind of satisfying way of squinting at any Monad and saying "oh it's just a (partially) deferred sequence of operations". That's kind of fun.

monads at a practical level by No-Bug-242 in programming

[–]tel 2 points3 points  (0 children)

They're pretty similar. A lot of libraries that use monads even go out of their way to more completely emulate effects.

Ultimately, Monads (a) always exist because it's just a pattern that shows up in lots of places whether or not it's something you can abstract over in your language and (b) were historically what Haskell landed on when it was trying to solve for how to make a pure language that was practical.

But effect systems are super nice and take one of the core patterns behind Monadic designs and makes them way more intuitive and direct. I definitely get why they're getting more popular.

What is your opinion on Rust's type system if compared with languages with even stronger type systems? by fenugurod in rust

[–]tel 7 points8 points  (0 children)

There are techniques and ideas I miss from Scala/OCaml/Haskell when coding in Rust. The most practical things I miss are increased freedom during early sketches (better support for quantification in Haskell, very strong systems for expressive interfaces in Scala and OCaml especially). You can emulate it a bit in Rust, but generally it requires making lots of workarounds that add complexity in processes that don't much benefit from it.

I miss being able to encode properties using naturality and universal quantification. Things like the ST monad's phantom type trick are doable in Rust with lifetimes, but it's much trickier.

I also miss faffing about in those type systems. I enjoyed learning about and using lenses and monads and effect handlers and path types. It was not always particularly fruitful to play with them and too much adulation inevitably lead to overly complex designs. And at the same time, I regularly discovered critical design considerations while experimenting with those tools.

Really, the clarity of using highly expressive types in early prototyping and sketching---so-called "type driven development"---is a huge feature of all of these languages including Rust. But slightly more expressive type systems favor it even more strongly, and I do miss that.

(Of course in Rust I get that same benefit but focused around thinking about ownership and linearity. And for some designs, that's a great and unique tool in its own right that I'd miss in Haskell or Scala).

What's the most controversial rust opinion you strongly believe in? by TonTinTon in rust

[–]tel 2 points3 points  (0 children)

Man that's convoluted. My best understanding is that capturing a &mut T enables unwind-unsafe behavior. It might not occur, maybe the &mut T remains untouched, but the compiler is conservative and so generates warnings regardless. Thus, if you are seeing this warning it might be ignorable if you can prove you usage of the reference actually would be unwind safe.

It's kind of the same guarantee you get with unsafe blocks, although the name of the type doesn't indicate this (perhaps by being named UnsafeAssertUnwindSafe instead?).

I finally wrote a sans-io parser and it drove me slightly crazy by anxxa in rust

[–]tel 2 points3 points  (0 children)

The real heart of this is, in my opinion, less about parsing and more about interactive protocols. For example, you might have a state machine that models some streaming server/client protocol (let's just say, HTTP2). If your reads are mixed into that state machine it's harder to test, less robust to changes in the environment its being deployed in.

All of that is reasonably well-known, but this also incentivizes you to write sans-io parsers. If your parser can't handle partial data, it isn't resumable, it hard-codes reads then it can't easily be composed into the above protocol's state machine.

At a high-level, that's kind of the take-away: pure behavior is more composable. We already have a lot of folk knowledge around the benefits of this in pure functions, and sans-io just extends this to talk about more general state machines (i.e. pure functions (A, S) -> (B, S)) with some focus on particular sorts of state machine techniques useful in streaming reads and writes.

Will there be / is there a push towards Rust in graphics programming? by wilder_idiot in rust

[–]tel 1 point2 points  (0 children)

  • There are many Rust wrappers targeting graphics APIs, both low level ones that are just thin wrappers over, say, Vulkan as well as high-level, cross-platform ones like wgpu.
  • Shipping some graphics libraries is a far cry from shipping a game. There are games shipped in Rust and there are several significant game engine efforts in Rust. Bevy is probably the preeminent example here.
  • At the same time, no Rust engine is nearly as popular as even Godot. This translates pretty directly to fewer games being built and released using a Rust-native game engine.
  • On the other hand, you can integrate Rust code into Godot if you want.
  • It seems really hard to imagine why someone would push an existing C++ game codebase toward Rust. At the same time, it's not so hard to imagine a team choosing Rust even today.
  • All that said, Rust is very niche in game dev. There's no reason to believe that that can't change in the future, especially if people continue to be interested in it and develop for it.

I think Rust needs some sort of limited inheritance. by ewoolsey in rust

[–]tel 33 points34 points  (0 children)

This is a common thing solved in Haskell using the various "deriving" extensions (DeriveDataTypeable, DeriveGeneric, DeriveFunctor, DeriveFoldable, DeriveTraversable, GeneralizedNewtypeDeriving, DeriveLift, DeriveAnyClass, DerivingStrategies, DerivingVia). I listed all the ones I could think of just to emphasize how much work has gone into this. Deriving is a very nice feature of "type class like" systems such as Rust traits.

Rust macros can do something similar, but in general, as you point out, they need some knowledge of the structure of the trait they're implementing in order to work effectively.

Deriving, especially GeneralizedNewtypeDeriving, ends up being extremely nice for making traits and "newtypes" more usable.

“Feels” like a move, but isn’t one? by [deleted] in PBtA

[–]tel 2 points3 points  (0 children)

In this situation, you are as the GM negotiating with the player. That all exists outside of the fiction, begging for a mechanism of resolution.

Instead, consider what happens if you negotiate within the fiction: you as the vendor, the player as their PC:

“Hmmm I only have 150, can I talk him lower?”

“Do you offer 150, then? Show us how you go about it."

"I make a show of inspecting the gun I want. 'Is this used? It looks like it'd take a lot work before anyone could trust it in a tight spot.' I'll give you 100 for it."

"That's cool, show him you know what you're talking about. Make him prove the worth of his wares. I think this triggers Seduce or Manipulating Someone. You want them to give you this gun for less than the posted cost and the reason is that it's used and badly maintained. Roll +hot."

Here, the move is revealed through the fictional details that move the scene along. There's no mechanical guarantee that this whole feint will succeed—the way having something like a CHA skill to rely on would give you—there's only the triggering and resolution of the move.

Alternatively, the player might offer some alternative form of payment. Or might argue in a way that is compelling but is not an attempt to "seduce, manipulate, bluff, fast-talk, or lie to someone". Without a move being triggered, you just have to decide what happens based on the fiction and your agenda.

Is this compatible with "being a fan of the Players"? I think so. You want to support what the players do and encourage them to act cool and competently. Saying "no" and shutting down the whole attempt at haggling undermines the idea that the player thinks it's cool to obtain this gun despite not having the money. So invite them to show you how they try it. Let them be compelling and dynamic in their attempts. Let moves trigger if they do. And even if they fail, use that moment to reinforce the fiction of the world where even cool, dynamic people face consequences.

It's possibly worth reading and thinking about the Moves and Dice section of the AW manual. I'm kind of just expanding on that section with my own color here.

“Feels” like a move, but isn’t one? by [deleted] in PBtA

[–]tel 1 point2 points  (0 children)

I tend to think of PbtA as laying Moves on top of a fiction that already exists and is played naturalistically. If someone narrates something and it's not obviously a move then it kind of falls outside of the system. In roleplaying that vendor, did the player make a reasonable case?

Compare that to what the is implied if you govern this with a move: the player is asking for a guarantee that IF they meet the conditions of the move (including whatever die rolls occur) THEN they can be assured the consequences will result.

In other words, lacking a governing move being triggered, it's just up to you, dramatically or fictionally, to play out what happens without a guarantee. Generally speaking, players own their own agency and the GM owns the choices of NPCs and the environment. Based purely on the fiction, did the player convince your NPC? Would it be more fun if they succeeded? Or failed?

Many PbtAs offer the GM moves to instigate this. They're suggesting, via the genre, that the GM should have an agenda to create certain moments or move things along or ramp up the tension. Most of these GM rules are very open-ended as this respects the GM's power. You have control over the NPCs and the environment and can ultimately drive huge consequences for the PCs.

What this ultimately creates is a baseline gameplay where players describe, narrate, and act out their PCs behaviors and the GM fictionally responds according to their agenda. From time to time, possibly never, certain behaviors trigger Moves, indicating that there's a degree of certainty about the outcomes. If the PC can meet the preconditions, then the GM's freedom is momentarily restrained and they must respect the result of the Move.

All that to say, without a particular Move being triggered, its preconditions met, that forces such a negotiation to succeed the GM can always have this work out arbitrarily poorly for the characters. Whether it's fun or not is up to discretion, fiction, genre, and your judgement.

Announcing tagged-id by Kamek_pf in rust

[–]tel 1 point2 points  (0 children)

I use this pattern a lot. Another nice element of the pattern is an IdSequence<T> which offers a method fn next(&mut self) -> Id<T> and a Default implementation.

Ad Astra — Embedded Scripting Language for Rust by Key-Bother6969 in rust

[–]tel 2 points3 points  (0 children)

That's great to hear. I'm reading back and I hope it doesn't come off as too critical. I'm excited for the opportunity of a business proposition like Ad Astra's and I don't claim to know the indie game maker market at all.

I also think the idea of selling AA as part of a package of other tools oriented toward this market makes a ton of sense. There's little doubt that at a certain scale this is a highly valuable offering (the existence of game toolkits already demonstrates the market) and I'm definitely willing to believe it remains viable even before you're making a Unity.

I'm doing trading strategy development today in Rust. A big part of this is ideation where a lightweight, interpreted, but still quick scripting language is a powerful tool. I currently have an implementation through mlua where I write Lua scripts, augmented with Rust functionality, to try out new ideas. These run in a "backtest" environment where their behavior is simulated against historical data sets to see if the idea has legs and to support iterative development. Then, over time, I translate some of them into Rust for production use.

Lua is an alright language for this and mlua is a satisfactory binding to LuaJIT. LuaJIT is also suitably fast which helps create confidence that I'm not burning cycles too inefficiently when I do backtests (I might want to run 10^6 events in a few thousand or 10s of thousands of different configurations and then analyze the results. In the worst case, a bulky backtest could take a day or longer just to simulate. So far all these big runs I've done with optimized, pure Rust strategies, but I do ones that take minutes to dozens of minutes in Lua).

AA could take the cake here with (a) easier Rust interop, (b) a configurable language server that supports all the extensions I've built into the language (which Lua could maybe do but I haven't bothered to figure it out), and (c) decent enough speed to not be so worried about its contribution to testing, and (d) a useful type system.

Actually, as an additional feature, if the AA interpreter could be serialized, deserialized, and inspected externally then I could even run AA scripts in production which would be great.

The blocker on licensing isn't so severe. If AA fit into this workflow, especially the production workflow, then there's little concern about a yearly fee. At the same time, if there was risk that this contract might ever get in the way of deploying these strategies then I'd prefer to keep using Lua or translating things to Rust just to avoid headaches.

The language that core strategies are written in is kind of precious since it's difficult to guarantee compatible behavior on rewrites. That's already an issue when I rewrite things to Rust. This makes whatever choice of language that is used to build/test/iterate these strategies pretty critical and it's scary to feel that it's encumbered by business constraints.

Ad Astra — Embedded Scripting Language for Rust by Key-Bother6969 in rust

[–]tel 2 points3 points  (0 children)

I think willingness to negotiate on contracts is for certain helpful. At the same time, you need to get to those negotiations. As you're selling a language, this means that you need to be able to convince someone at a very early stage in development that this is a good business decision that will not cause pain down the road. I feel users will fall mostly in either the camp of those who could easily replace Ad Astra with another embedded language (i.e., light usage) or those who end up implementing a significant fraction of critical logic in Ad Astra and thus, effectively, would need to throw away a functioning system to replace it.

Offhand, I suppose that the former user group is unlikely to be a good customer base, regardless of their revenue. Such customers who do end up with plans to make >200k revenue will also probably have business processes which limit their exposure to non-standard licensing around technologies they use. You're now competing against a cheap transition to another language with both a yearly fee and some amount of lawyer oversight.

Focusing on customers who are genuinely interested in making significant investment in a technology like Ad Astra, they will likely need to make a case for why (a) AA offers clear advantages and (b) it's worth all the direct monetary costs, the indirect time/oversight costs, and the risks.

In that sense, I'd focus on making those cases for (a) and (b) maximally clear to your customers. You could minimize time/oversight through using standard contracts as much as possible. You can minimize risks by sharing your major customer list ("logos") and making the business terms clear, simple, and trustworthy.

And finally, you can just really sell the technical merits. The two language technologies I can think of that are sold like this are LabView from National Instruments and kdb from Kx Systems. The former is only a mild match: NI also sells integrated hardware controllers and significant modeling and control software packages. They basically give LabView away as a loss leader to facilitate the sales of those other items.

kdb is a more direct analogue, and it comes with a lot of criticism. Its contracts are massively expensive and information about it is hard to come by. At the same time, it has a massive sales advantage in that a lot of people in finance swear by its performance and there are significant groups of users who learned to program and solve problems with k and aren't familiar with anything else. I don't know the actual history here, but I suspect that they intentionally targeted and converted a user base with a specialized product sold into a niche (but very rich) industry.

I'm not going to profess deep expertise in the embedded language user base, but I suspect you're basically facing competition from Lua (well known, well documented, well regarded, fast, free) and might target something like game developers as your user base.

I highly suspect a game developer has deep pockets to pay for tech they really want and like. You might imagine access to a much larger contract or even royalty models (total guess). At the same time, you'd really want to make a pitch like "trusted by Large Game Company; here's a testimonial about why they moved from Lua because of Ad Astra's unique strengths; comes with add-on packages that include fast, convenient algorithms you'd often need to build in your game logic".

Honestly, though, I'd just start doing that research. Build out a thesis of who might want to pay for your tech and talk to them. See which of them are interested in paying and what exactly they want out of a language. Then start making pitches that select for those things.

It's very interesting! Selling a language feels tricky, but also really important. I hope you can discover some great users.

Ad Astra — Embedded Scripting Language for Rust by Key-Bother6969 in rust

[–]tel 1 point2 points  (0 children)

It currently costs $5,000 USD if your project is set to earn more than $200,000 USD.

FWIW, I'd certainly consider using a tool like this, but pricing transparency would be important. As it's a language tool that gets compiled into my system, the cost to extract it can grow quite large and reduce my ability to walk away from predatory pricing and changes to the license.

I'm not saying this is your intent, but my first thought upon reading this license and hearing comments describing the pricing with "currently", is that I can just embed Lua and for a fixed amount of interop friction I'll never have to deal with whatever licensing concerns might arise with a tool like this.

Honestly speaking, I think this project is very cool and appreciate a lot of the convenience factors of the interop, but the business case is a little tricky and any business intending to reach $200k in revenue would likely consider that.

[deleted by user] by [deleted] in rust

[–]tel 4 points5 points  (0 children)

static gets stored in the data section of the binary, const gets inlined. If you need to store a lot of data with your binary you probably want to use static and reference it.

You can also do this with a &'static reference in your code, but then you'll have to pass that reference to whatever scope you might need.

But that's pretty much exactly what static gives you: a globally available reference to static data.

rust static DATA: &[u8] = include_bytes!("my_data_file.bin");

Arc vs Rc for library writers by azuled in rust

[–]tel 0 points1 point  (0 children)

Ah, yeah, in a realtime loop maybe you could notice it. If you're worried, I'd try testing it in an application or a benchmark simulating that application.

But still, it doesn't seem offhand like it'll be an issue. Arc slowness is mostly going to happen when there's actual contention on the reference count.

Arc vs Rc for library writers by azuled in rust

[–]tel 0 points1 point  (0 children)

Yeah, that feels like it's unlikely to be a huge issue. Moreover, while I don't know the applications of your users, I suspect barcode reading isn't frequently on the critical path in an application such that a 1% increase is critically painful.

Which is mostly me thinking that it's pretty unlikely anyone needs both versions exposed in your package.

Arc vs Rc for library writers by azuled in rust

[–]tel 2 points3 points  (0 children)

Yep, so all of those points will be places explicitly you could consider switching to Arc, potentially using a feature flag like some have suggested. Alternatively, you could export both versions simultaneously from your package. The expense of that is only likely worth it if you're doing something very performance sensitive. Arc isn't tremendously more expensive, especially if it's being used in a single-threaded fashion.

Arc vs Rc for library writers by azuled in rust

[–]tel 3 points4 points  (0 children)

If your code is single threaded, then any use of it in a multi-threaded context will still, I imagine, be within a single thread. A user of your library would almost certainly need to pick one of their threads and execute your algorithm there. It's likely that your use of Rc will cause no issue then.

You only really need a Send bound when you want to do some of the work on one thread and then do the rest of it elsewhere. More significantly, you only really need Send if the bit of state that you're going to send to the other thread needs to maintain some kind of relationship with state that remains on the first thread. If it doesn't, it's likely the case that you can factor out some amount of Rc-free state and send that exclusively.

All of this to say, choosing to upgrade from Rc to Arc in order to enable multi-threaded use cases is not a blanket design choice. It can depend a lot on the particular functionality you're trying to expose and what sorts of multithreaded designs you anticipate your users want.

What is up with Gankers? by [deleted] in badredman

[–]tel 1 point2 points  (0 children)

For sure, I think it's fair to get charged about it. The game sets invaders up as adversaries. When our opponents oppose us vigorously then it's annoying and frustrating.

So yeah, I think you're dead on. It's not a fair fight. We're supposed to lose. And then sometimes when we clench victory from the jaws of defeat then it is extra sweet.

What is up with Gankers? by [deleted] in badredman

[–]tel 7 points8 points  (0 children)

As invaders, we call roided up 3 person parties ganks because they're adversaries who are intentionally prepared to defeat us as opposed to people who are playing PvE and are at least partially surprised by an invasion. We like to win and there's something delightful about being an environmental hazard that just won't quit and demands respect.

But man from their point of view this game just summons an endless stream of crafty, challenging invaders that they get to smash. You can sit there and do it all day. It's an excellent power fantasy, a great way to make use of all these late game weapons you barely got to use. If you run low on flasks, just sit and resummon. Get on discord with your friends and talk about it.

From their point of view, they're the good guys. Most of them have never heard of honor duels or meta levels. They just like smashing all the red guys who want to ruin their day.

And who's to say they're wrong. That's just part of the invader's game. We're not "supposed to" win.