41

如何从stdinDart 中读取控制台输入?

scanfDart 中有一个吗?

4

8 回答 8

55

stdinreadLineSync()方法允许从控制台捕获字符串:

import 'dart:convert';
import 'dart:io';

void main() {
  print('1 + 1 = ...');
  var line = stdin.readLineSync(encoding: utf8);
  print(line?.trim() == '2' ? 'Yup!' : 'Nope :(');
}

旧版:

import 'dart:io';

main() {
    print('1 + 1 = ...');
    var line = stdin.readLineSync(encoding: Encoding.getByName('utf-8'));
    print(line.trim() == '2' ? 'Yup!' : 'Nope :(');
}
于 2013-08-12T11:57:17.223 回答
18

以下应该是从标准输入读取输入的最新 dart 代码。

import 'dart:async';
import 'dart:io';
import 'dart:convert';

void main() {
  readLine().listen(processLine);
}

Stream<String> readLine() => stdin
    .transform(utf8.decoder)
    .transform(const LineSplitter());

void processLine(String line) {
  print(line);
}
于 2013-10-15T20:33:22.990 回答
12
import 'dart:io';

void main(){
  stdout.write("Enter your name : ");
  var name = stdin.readLineSync();
  stdout.write(name);
}

输出

Enter your name : Jay
Jay

默认情况下 readLineSync() 将输入作为字符串。但是如果你想要整数输入,那么你必须使用 parse() 或 tryparse()。

于 2019-01-18T12:36:05.917 回答
4

使用像 StringInputStream 这样的 M3 dart 类被替换为Stream,试试这个:

import 'dart:io';
import 'dart:async';

void main() {
  print("Please, enter a line \n");
  Stream cmdLine = stdin
      .transform(new StringDecoder())
      .transform(new LineTransformer());

  StreamSubscription cmdSubscription = cmdLine.listen(
    (line) => print('Entered line: $line '),
    onDone: () => print(' finished'),
    onError: (e) => /* Error on input. */);


}
于 2013-03-15T18:55:26.253 回答
2

从 Dart 2.12 开始,启用了 null-safety,stdin.readLineSync()现在返回 aString?而不是 a String

这显然让很多人感到困惑。我强烈建议阅读https://dart.dev/null-safety/understanding-null-safety以了解 null-safety 的含义。

具体来说stdin.readLineSync(),您可以通过检查nullfirst 来解决此问题,对于局部变量,它会自动将 a 提升String?为 a String。这里有些例子:

// Read a line and try to parse it as an integer.
String? line = stdin.readLineSync();
if (line != null) {
  int? num = int.tryParse(line); // No more error about `String?`.
  if (num != null) {
    // Do something with `num`...
  }
}
// Read lines from `stdin` until EOF is reached, storing them in a `List<String>`.
var lines = <String>[];
while (true) {
  var line = stdin.readLineSync();
  if (line == null) {
    break;
  }
  lines.add(line); // No more error about `String?`.
}
// Read a line.  If EOF is reached, treat it as an empty string.
String line = stdin.readLineSync() ?? '';

请注意,您不应该盲目地这样做stdin.readLineSync()!readLineSync返回 aString?是有原因的:它null在没有更多输入时返回。使用空断言运算符( !) 要求运行时异常。

于 2021-04-06T09:03:31.860 回答
1

请注意,虽然调用stdin.readLineSync()您的isolate/thread将被阻止,但不会Future完成其他任何操作。

如果你想stdin String异步读取一行,避免isolate/thread阻塞,这是这样的:

import 'dart:async';
import 'dart:convert';
import 'dart:io';

/// [stdin] as a broadcast [Stream] of lines.
Stream<String> _stdinLineStreamBroadcaster = stdin
    .transform(utf8.decoder)
    .transform(const LineSplitter()).asBroadcastStream() ;

/// Reads a single line from [stdin] asynchronously.
Future<String> _readStdinLine() async {
  var lineCompleter = Completer<String>();

  var listener = _stdinLineStreamBroadcaster.listen((line) {
    if (!lineCompleter.isCompleted) {
      lineCompleter.complete(line);
    }
  });

  return lineCompleter.future.then((line) {
    listener.cancel();
    return line ;
  });
}

于 2021-03-04T00:21:59.703 回答
0

所有这些基于异步 API readLine*() 的解决方案都缺少语法糖,它使您能够在没有同步阻塞的情况下做所有事情,但编写得像同步代码。这在您编写代码以同步执行的其他语言中更加直观:

import 'dart:convert';
import 'dart:io';

Future<void> main() async {
  var lines = stdin.transform(utf8.decoder).transform(const LineSplitter());
  
  await for (final l in lines) {
    print(l);
  }
  print("done");
}

这里的关键点是使用asyncand await

  • async在您的方法上是必需的,因为您await用于与异步 API 调用交互
  • await for是在 a 上执行“类同步”代码Stream的语法(a 的相应语法Future是 just await)。

一旦有东西可以处理,就可以通过让下面的代码执行来为你await“解包”一个Stream/ 。Future现在您不再阻塞您的主线程 ( Isolate) 来完成这项工作。

有关更多信息,请参阅关于 async/await的Dart 代码实验室。

(旁注:为函数声明任何返回值的正确方法async是将其包装在 a 中Future,因此Future<void>在这里。)

于 2022-01-06T21:16:48.773 回答
0

您可以使用以下行从用户那里读取字符串

String str = stdin.readLineSync();

或以下行读取数字

int n = int.parse(stdin.readLineSync());

考虑以下示例:

import 'dart:io'; // we need this to use stdin
void main()
{
    // reading the user name
    print("Enter your name, please: ");
    String name = stdin.readLineSync();
  
    // reading the user age
    print("Enter your age, please: ");
    int age = int.parse(stdin.readLineSync());
  
    // Printing the data
    print("Hello, $name!, Your age is: $age");
  
  /* OR print in this way
   * stdout.write("Hello, $name!, Your age is: $age");
   * */
}
于 2021-03-24T15:02:13.357 回答