EXC_BAD_ACCESS 使用 Default::default() 时

EXC_BAD_ACCESS when using Default::default()

我有一个看起来很简单的结构,我在其中实现了默认特征:

#[derive(Debug, PartialEq)]
pub enum AuthenticationType {
  Trust,
  AuthenticationCleartextPassword,
  AuthenticationMD5Password,
  AuthenticationSASL,
}

#[derive(Debug)]
pub struct Configuration {
  user: String,
  password: Option<String>,
  dbname: Option<String>,
  hostaddr: SocketAddr,
  authentication_type: AuthenticationType,
}

impl Configuration {
  pub fn new(user: String, password: Option<String>, dbname: Option<String>, hostaddr: SocketAddr, authentication_type: AuthenticationType) -> Self {
    Configuration {
      user,
      password,
      dbname,
      hostaddr,
      authentication_type,
    }
  }
}

impl Default for Configuration {
  fn default() -> Self {
    Configuration {
      hostaddr: SocketAddr::new(IpAddr::V4(Ipv4Addr::new(127, 0, 0, 1)), 5432),
      authentication_type: AuthenticationType::Trust,
      ..Default::default()
    }
  }
}

以及导致堆栈溢出的默认方法的测试:

#[cfg(test)]
mod tests {

  use super::*;

  #[test]
  fn test_default_configuration() {
    let configuration = Configuration::default();
    //assert_eq!(configuration.authentication_type, AuthenticationType::Trust);
  }
}

使用 VSCode 进入默认方法我在调用 ..Default::default() 时得到一个 EXC_BAD_ACCESS

我确定我遗漏了一些明显的东西,但无法弄清楚它是什么?

impl Default for Configuration {
  fn default() -> Self {
    Configuration {
      hostaddr: SocketAddr::new(IpAddr::V4(Ipv4Addr::new(127, 0, 0, 1)), 5432),
      authentication_type: AuthenticationType::Trust,
      ..Default::default()
    }
  }
}

在上面的代码中 Default::default() 有一个推断的 return 类型的配置,因为 .. 语法表明你想使用指定的字段值和来自Configuration.

类型的值

由于 Default::default() 具有 Configuration 的推断 return 类型,它调用 Configurationdefault 实现,这导致无限递归。

无限递归导致堆栈溢出,表现为访问堆栈末尾的无效内存,导致 EXC_BAD_ACCESS