简体   繁体   English

我可以定义必须执行`!Send`的特征吗?

[英]Can I define a trait whose implementations must be `!Send`?

I'd like to define a trait which forces its implementors to under no circumstances be sent to, or shared between, threads. 我想定义一个特征,该特征迫使它的实现者在任何情况下都不能发送到线程或在线程之间共享。 It should suffice to mark the trait as !Send , but Rust doesn't seem to let me. 将特征标记为!Send就足够了,但是Rust似乎没有允许我。

Is it possible? 可能吗?

Example ( playground ): 示例( 操场 ):

#![feature(optin_builtin_traits)]

// This is a syntax error
//trait ThreadThing : !Send {}

// This doesn't work either
trait ThreadThing { }
impl !Send for ThreadThing {}

No, you can't make !Send a condition of ThreadThing . 不,您不能!Send ThreadThing条件。 The compiler just doesn't support that kind of logic. 编译器只是不支持这种逻辑。

If it would be possible for someone using your crate to make a type that is implicitly Send , contains no unsafe code in its implementation anywhere, and make it unsafe just by implementing ThreadThing for it -- in that case, you would make ThreadThing an unsafe trait to indicate that there is unsafe code somewhere that relies on an invariant that can't be described in the type system: the invariant "Things that are Send don't implement ThreadThing ". 如果某人可能使用您的板条箱创建一个隐式Send的类型,则在其实现中的任何地方均不包含不安全的代码,并仅通过ThreadThing实现ThreadThing 使其不安全 -在这种情况下,您将使ThreadThing unsafe trait ,表明某个地方存在不安全代码,该代码依赖于类型系统中无法描述的不变式:不变式“ Send事物未实现ThreadThing ”。

If, as is more likely, it's only unsafe to implement Send manually for a type that implements ThreadThing -- in that case, you don't need to do anything, because manually implementing Send is unsafe already . 如果很可能对于实现ThreadThing的类型手动实现Send只是不安全的-在这种情况下,您无需执行任何操作,因为手动实现Send已经不安全了 If an implementor of ThreadThing decides to manually implement Send , they take on the burden of guaranteeing not only their own invariants, but also ThreadThing 's. 如果ThreadThing的实现者决定手动实现Send ,则他们不仅要保证自己的不变式,还要ThreadThing的不变性。

The answer is: yes, you can, under some very specific conditions. 答案是:是的,您可以在某些非常特定的条件下进行操作。 Whether you should need to do this is another matter. 是否需要执行此操作是另一回事。

You can define a negative trait implementation for another trait if the trait you are negating is: 如果要否定的特征是,则可以为另一个特征定义否定特征实现:

  • an auto-trait. 自动特征。
  • from the current crate. 从当前的箱子里。

So the following will work ( playground ): 因此,以下将工作( 操场 ):

#![feature(optin_builtin_traits)]

auto trait Scary {}

trait ThreadThing { }
impl !Scary for ThreadThing {}

But it would not work if you were trying to do: 但是,如果您尝试这样做,将无法正常工作:

impl !Send for ThreadThing {}

Or if Scary was not an auto-trait. 或者,如果Scary不是自动特征。

Note however that, in general it should not be necessary to mark a trait !Send in this way. 但是请注意,通常不必标记特征!Send以这种方式!Send The concrete implementations of the trait will be marked Send or !Send by the Rust compiler based upon the contents of the implementing struct. 特质的具体实现将由Rust编译器根据实现结构的内容标记为Send!Send

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 发送只能针对结构体/枚举类型而不是特征来实现 - Send can only be implemented for a struct/enum type, not a trait 将发送特征添加到装箱特征对象时的奇怪行为 - Strange behavior when adding the Send trait to a boxed trait object 可以在自己的线程中运行的结构的特征 - Trait for a struct that can be run in its own thread 我可以为ThreadPool.QueueUserWorkItem定义频率检查吗? - Can I define frequency check for ThreadPool.QueueUserWorkItem? 如何将函数发送到另一个线程? - How can I send a function to another thread? 如果向其活动不可见的处理程序发送消息会发生什么? - What will happen if send message to handler whose activity has been unvisible? 我可以在Iphone的后台将位置发送到服务器吗? - Can I send locations to a server in background on Iphone? 线程中使用的所有内容都必须在 Rust 中“发送”吗? - Must everything used in thread be `Send`able in Rust? Qt Worker线程-必须为每个特定任务继承还是可以使用回调? - Qt Worker thread - must I inherit for every specific task or can I use a callback? Rust 2021 与 2018:特征 `std::marker::Send` 未实现 - 在 2021 版中执行此操作的正确方法是什么? - Rust 2021 vs. 2018: trait `std::marker::Send` is not implemented - what is the correct way to do this in 2021 edition?
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM