PHPFixing
  • Privacy Policy
  • TOS
  • Ask Question
  • Contact Us
  • Home
  • PHP
  • Programming
  • SQL Injection
  • Web3.0

Monday, December 12, 2022

[FIXED] What does “&*” do in Rust?

 December 12, 2022     rust, syntax     No comments   

Issue

I encountered this block of code while reading documentation from a Rust library:

for (ent, pos, vel) in (&*entities, &mut pos_storage, &vel_storage).join() {
    println!("Processing entity: {:?}", ent);
    *pos += *vel;
}

What does &*entities do here? From what I can tell it’s dereferencing entities and then referencing it again. But why?


Solution

This is an explicit reborrow and it's a common idiom that pops up in Rust from time to time.

  • & in an expression only has one meaning: it takes an expression (which must be a place expression) of type T and borrows a reference to it of type &T.

  • For references, * does the opposite of & -- it takes a reference (&T) and makes a place expression of type T. But * can mean different things with different kinds of pointers, since you can override it by implementing Deref. Because * ties in some compiler magic that automatically dereferences the return value of Deref::deref, you can borrow the result of *, turning it back into a plain reference, by using the & operator.

So &*foo is a way of explicitly reborrowing "any kind of pointer to T" as a &T, and is the equivalent of manually calling Deref::deref(&foo).

(The above explanation also works for &mut borrows -- just replace & with &mut and Deref with DerefMut.)

It's not clear in the example you link what entities is, but it's probably some kind of smart pointer, where the join() method requires a plain reference. For another example where this is required, consider using [&str]::concat to concatenate a String with some &strs:

// I want to concatenate this with some other strings
let s = String::from("Amelia");
// The following won't compile: you can't make an array of &str and String
assert_eq!(["Hello", ", ", s].concat(), "Hello, Amelia");    // WRONG
// However, &*s takes a reference to the str pointed to by s.
assert_eq!(["Hello", ", ", &*s].concat(), "Hello, Amelia");  // OK

See also

  • Is there a difference between slicing and an explicit reborrow when converting Strings to &strs?
  • Box<T> to &T in Rust


Answered By - trent
Answer Checked By - Robin (PHPFixing Admin)
  • Share This:  
  •  Facebook
  •  Twitter
  •  Stumble
  •  Digg
Newer Post Older Post Home

0 Comments:

Post a Comment

Note: Only a member of this blog may post a comment.

Total Pageviews

Featured Post

Why Learn PHP Programming

Why Learn PHP Programming A widely-used open source scripting language PHP is one of the most popular programming languages in the world. It...

Subscribe To

Posts
Atom
Posts
Comments
Atom
Comments

Copyright © PHPFixing