Questioning the dereference operator notation

I understand denoting the dereference operator with * comes from C, but in my opinion Rust differs enough from C to make uniform notation not very important. The fact that * is also the multiplication operator makes mathematical expressions more difficult to understand. Consider for instance the following expression:

*a**x/*z-*d**e

I found at least two recent threads regarding the dereference operator notation:

I wonder why * was chosen (apart from uniformity with C) instead for instance of either one of $, @, ~. In particular $ is already used by other languages:

Here is the example above written with different notations, either one of these expressions in my opinion is better than the original:

$a*$x/$z-$d*$e
@a*@x/@z-@d*@e
~a*~x/~z-~d*~e

I think the idea is that almost every operator in Rust comes from C and they do the same thing as they do in C, for better or for worse. Even & in Rust is used for similar purposes. The reason is probably just to have syntax that is familiar to C/C++ users and to have at least one aspect already be immediately familiar.

And style-wise, I always put spaces between binary operators and their expressions while having no spaces between * and the variable being dereferenced, which makes things a little more clear.

*a * *x / *z - *d * *e

This is also what is recommended in the Rust style guidelines.

Well, @, and ~ used to be different pointer types in Rust, so those would have never been considered.

But generally speaking, languages only have a certain amout of 'weird quotient.' Change for change's sake can be worse than no change at all. Uniformity with C family languages, and, I'd argue, the vast majority of other languages, is a feature. The Wikipedia page you linked to even calls * the operator, and then notes a few alternate syntaxes below.

Thanks for your answers. I believe * notation is specific for C/C++. It was born when characters available were limited, and for the same reason it has even a broader meaning in C/C++. C#, which is strictly related to C/C++, adopted it. However many other languages use a different notation. For instance F# uses !, Pascal/Delphi uses ^, other languages use $, etc.

I made a brief research online and found many threads talking about this issue with C/C++ as well... I'm happy to know that I'm not the only one :smile:

Using $ notation, the expression above with correct spacing becomes:

$a * $x / $z - $d * $e

which looks much better to me.

Not to say that I do not like Rust for this of course, just food for thought to possibly make it better...

1 Like

Now that we have hit beta, a change as sweeping as this is almost assured to never happen.

Also, in a world where we did switch the sigil to $, we would go back to being berated as a perl-esque language of terribleness. Id rather not go back to that, regardless of the correctness of that statement.

which looks much better to me.

Ok so its completely subjective. I like *, and i think it looks better. Also your argument is kind of misleading, in the OP you said "this is bad looking" becuase you didnt put any whitespace in to clarify the code, whereas in your latest post, you added whitespace which simplifies reading.

$a*$x/$z-$d*$e

I think this looks just as bad. But of course "I think" means that this is subjective, just like this entire thread.

I confirm the topic is subjective, but I need to explain that the expression with added whitespace should not be compared with the one in my original post but with the one in @reklawnos answer.

So the comparison is:

*a**x/*z-*d**e
$a*$x/$z-$d*$e

or:

*a * *x / *z - *d * *e
$a * $x / $z - $d * $e

Both of them look to me (subjective) more clear with $ notation. If $ is too perl-esque, @ could be used instead (meaning the value at that memory location).

I agree with you that the $ looks more clear and prevents conflicts between * for dereferencing and * for multiplication, but the cost to clarity is weighed against the cost of losing some consistency, having users learn the new notation, and forcing people to fix existing Rust code as this is a severe breaking change. The reality is that the only time this is ever a problem when trying to multiply and dereference as part of the same expression, which occurs less frequently in Rust than simply dereferencing.

The $ looks nice, sure, but Rust is past the phase where this can be changed.

Note that the basic types, floats and integers, allow arithmetic on references as well as values, so in non-generic context at least, it's simple to just leave off the dereferencing entirely:

let a = &1.;
let b = &2.;
a / b    // equals 0.5

$ is, I am sorry, quite ugly. The @ is, indeed, quite expressive, but ugly, too:

@a * @x / @z - @d * @e

But then, it might just be my C spoiled eyes that like the * way more. Especially in the way written according to the Rust style guide.

Edit: I'd prefer @ over $ and would get used to it very soon. But then, it is probably way to late to argue about it, really.

( *a) *( *x) / ( *z) - ( *d) * (*e)

I agree @ would be the best choice. I recap here the main reasons why IMO @ would be preferable over *:

  • More expressive, clearly states that I am referring to the value at that memory location.
  • More visible in the code, source code highlighters could manage it better, similarly to &.
  • Mathematical expressions and in general expressions involving arithmetic operators would be clearer to read.
  • The * character has a broader meaning in C/C++, so it may actually be preferable to deviate from it to avoid confusion.

I know we hit beta already... but the change would not be difficult. During the transition time, the compiler could manage both notation, and emit a warning such as "the * dereference operator is deprecated, use @ instead, this may not compile in future".

[quote="lucatrv, post:11, topic:836"]
clearly states that I am referring to the value at that memory location.
...
The * character has a broader meaning in C/C++
[/quote]Have you seen the list of Deref implementors?

De have hit beta of the 1.0 release, after years of development. Syntax has changed before, but it is now truly very late.

In C * is used also for declaration: int* const * npp = &np;

You mean like *const *mut i32?

Yes, I see that as the C equivalent (unsafe), so for that purpose IMO * would be ok.
I understand it's a late discussion though...