Правильно ли мое понимание следующего кода reqwest в Rust? - PullRequest
0 голосов
/ 18 апреля 2020

Я играл с Rust и наткнулся на следующий код:

fn request(&url) -> Result<(), Box<dyn std::error::Error>> {
  let mut res = reqwest::get(&url)?;
  let mut body = String::new();
  res.read_to_string(&mut body)?;
  println!("Status: {}", res.status());
  println!("Headers:\n{:#?}", res.headers());
  println!("Body:\n{}", body);
  Ok(())
}

Насколько я понимаю, что:

fn request(&url) -> Result<(), Box<dyn std::error::Error>> {

Определяет функцию, которая имеет единственный (заимствованный) параметр и использует Result для обработки ошибок.

  let mut res = reqwest::get(&url)?;

Определяет изменяемую переменную для хранения объекта ответа из метода get ящика *1013*.

  let mut body = String::new();

Определяет изменяемую переменную для хранения строки responseText.

  res.read_to_string(&mut body)?;

Этот метод сохраняет responseText в переменной body.

  println!("Status: {}", res.status());
  println!("Headers:\n{:#?}", res.headers());
  println!("Body:\n{}", body);

Печатает три отформатированные строки (с завершающими новыми строками), содержащие статус ответа, заголовки и тело.

  Ok(())

Обрабатывает ошибки с помощью Result ..?


Вопросы:

  1. Что означают / делают пустые скобки в Result<() и OK(())?
  2. Что такое Box<dyn std::error::Error>?

1 Ответ

1 голос
/ 06 мая 2020

Вы абсолютно правы в своем понимании.

  1. Результатом является Enum, который может быть либо "Ok", либо "Err" - если Ok, тогда может быть какое-то значение в порядке (результат, ответ, данные, вывод, что угодно); Точно так же, если Err, то есть какая-то конкретная ошибка, о которой вы можете сообщить. С этим давайте разберем результат.

    Следует читать так: Result<TypeOfValueIfOkay, TypeOfErrorWhenNotOkay>. Эти два подтипа могут быть чем угодно, но они должны быть чем-то - нельзя просто игнорировать это.

  2. Так что, если TypeOfValueIfOkay должно быть чем-то, но если вы не Если вы не хотите что-то возвращать, вы можете вернуть пустой Tuple . Это () в результате. Он просто говорит: «Я вообще ничего не возвращаю, когда все идет хорошо».

  3. Итак, вторая часть TypeOfErrorWhenNotOkay также может быть просто любого типа - строка, целое число, что угодно , Для типа помогает реализовать черту std::error::Error, помогающую вызывающим абонентам немного стандартизироваться.

    Для возврата «некоторого динамического c объекта, который реализует черту std::error::Error», требуется, чтобы Rust знал точный размер этого значения, если он должен вернуть его в стеке вызывающей стороны (размер стека вызывающей стороны должен быть измерен принять его.)

    Вот тут и появляется тип Box - он помещает фактическое значение в кучу и содержит указатель на него (который может иметь предсказуемый фиксированный размер независимо от фактического значения на куча.) <dyn std::error::Error> является гарантией того, что независимо от значения в штучной упаковке, он реализует черту Error.

  4. Так что теперь финальный Ok(()) имеет смысл. Если вы читаете Ok(value): он говорит, что перечисление Result является вариантом Ok со значением "empty tuple" (), то есть ничего.

...