首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >如何解析类型参数“T”所需的不能推断类型的类型注释?编译这段代码需要什么类型的注释?

如何解析类型参数“T”所需的不能推断类型的类型注释?编译这段代码需要什么类型的注释?
EN

Stack Overflow用户
提问于 2022-05-23 07:21:26
回答 1查看 691关注 0票数 0

块链结构定义,它定义一个类型,而我使用该类型

代码语言:javascript
复制
pub struct Blockchain<T = SledDb> {
    pub storage: T,
    pub chain: Vec<Block>,
    pub tip: Arc<RwLock<String>>,
    pub height: AtomicUsize,
    pub mempool: Mempool,
    pub wallet: Wallet,
    pub accounts: Account,
    pub stakes: Stake,
    pub validators: Validator,
}

这段代码正在检查桩是否是valid.The代码,用于挖掘一个块,错误由is_staking_valid函数来模拟。我不知道它要什么类型的,因为我已经指定了一个。

代码语言:javascript
复制
impl<T: Storage> Blockchain<T> {
    pub fn is_staking_valid(
            balance: u64,
            difficulty: u32,
            timestamp: i64,
            prev_hash: &String,
            address: &String,
        ) -> bool {
            let base = BigUint::new(vec![2]);
            let balance_diff_mul = base.pow(256) * balance as u32;
            let balance_diff = balance_diff_mul / difficulty as u64;
    
            let data_str = format!("{}{}{}", prev_hash, address, timestamp.to_string());
            let sha256_hash = digest(data_str);
            let staking_hash = BigUint::parse_bytes(&sha256_hash.as_bytes(), 16).expect("msg");
    
            staking_hash <= balance_diff
        }
    pub fn mine_block(&mut self, data: &str) -> Option<Block> {

        if self.mempool.transactions.len() < 2 {
            info!("Skipping mining because no transaction in mempool");
            return None;
        }

        let balance = self
            .stakes
            .get_balance(&self.wallet.get_public_key())
            .clone();

        let difficulty = self.get_difficulty();
        info!("New block mining initialized with difficulty {}", difficulty);

        let timestamp = Utc::now().timestamp();
        let prev_hash = self.chain.last().unwrap().hash.clone();
        let address = self.wallet.get_public_key();


        if Blockchain::is_staking_valid(balance, difficulty, timestamp, &prev_hash, &address){

        let block = self.create_block(&data, timestamp);
        self.storage.update_blocks(&prev_hash, &block, self.height.load(Ordering::Relaxed));
        Some(block)
        } else {
           None
        }
    }
}

请查找下面的编译器错误

代码语言:javascript
复制
error[E0282]: type annotations needed
   --> src/blocks/chain.rs:173:12
    |
173 |         if Blockchain::is_staking_valid(balance, difficulty, timestamp, &prev_hash, &address){
    |            ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ cannot infer type for type parameter `T`

For more information about this error, try `rustc --explain E0282`.
EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2022-05-23 11:31:32

最小化示例:

代码语言:javascript
复制
pub struct Blockchain<T> {
    pub storage: T,
}

impl<T> Blockchain<T> {
    pub fn is_staking_valid() {
        todo!()
    }
    pub fn mine_block(&mut self) {
        Blockchain::is_staking_valid();
    }
}

游乐场

造成此错误的原因是,Blockchain::<T1>::is_staking_validBlockchain::<T2>::is_staking_valid既是两个独立的、完全无关的函数,也与编译器有关。是的,它们有相同的代码,是的,它们将被优化器重复使用,但是这并不一定是这样的--例如,如果这个函数使用了T上可用的关联项

代码语言:javascript
复制
trait Stakable {
    const IS_VALID: bool;
}
impl Stakable for () {
    const IS_VALID: bool = false;
}
impl Stakable for i32 {
    const IS_VALID: bool = true;
}

struct Blockchain<T> {
    pub _storage: T,
}

impl<T: Stakable> Blockchain<T> {
    fn validate() {
        if !T::IS_VALID {
            panic!("Type is not valid");
        }
    }
}

fn main() {
    // This panics - we catch this panic and show that it has indeed happened
    std::panic::catch_unwind(|| Blockchain::<()>::validate()).unwrap_err();
    // This executes successfully
    Blockchain::<i32>::validate();
}

游乐场

由于可能存在歧义,编译器拒绝自行选择,并强制您显式地进行选择。

因此,您有几种可能的方法:

  • 使is_staking_valid成为一个自由函数,而不是Blockchain的关联函数。在这种情况下,它将不能依赖于Blockchain的类型参数,因此调用将是明确的。
  • 调用Self::is_staking_valid而不是Blockchain::is_staking_valid。在这种情况下,Self将被替换为Blockchain::<T>,从当前执行的方法中提取T;这将再次解决歧义。
  • 使is_staking_valid成为Blockchain上的一个方法,即使其接收&self,并通过self.is_staking_valid()调用它。
  • 不建议,但仍有可能-使is_staking_valid成为Blockchain<T>上的一个特定T的关联函数,例如:
代码语言:javascript
复制
pub struct Blockchain<T> {
    pub storage: T,
}

impl Blockchain<()> {
    // Note - no free type parameters here!
    pub fn is_staking_valid() {
        todo!()
    }
}

impl<T> Blockchain<T> {
    pub fn mine_block(&mut self) {
        // Here, `Blockchain` is `Blockchain::<()>` - the method is set
        Blockchain::is_staking_valid();
    }
}
票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/72344636

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档