我很难找到有关System.in.read();
如何运作的细节,也许有人可以帮助我。看起来像扫描仪会更好,但我不允许使用它。
我得到了一个任务,我应该以Boolean-Operator-Boolean的形式读取控制台用户输入,例如T ^ F或T& T通过System.in.read()
并简单地打印语句返回的内容。
普通人可能会使用不同的方法,但该作业明确指出只允许System.in.read()
和System.out.println()
。
这是我尝试解决它:
import java.io.*;
public static void main(String[] args) {
String error = "Reading error, please use T or F";
boolean a = true; //char: 84 or 116 for T and t
boolean b = false; //char: 70 or 102 for F and f
int userChar1;
int userOperator;
int userChar2;
int chosenOperator = 0;
try {
//Get first char
System.out.println("Enter the first value (T or F):");
userChar1 = System.in.read();
if((userChar1==84)||(userChar1==116)) { // T or t
a = true;
} else if ((userChar1==70)||(userChar1==102)) { // F or f
a = false;
} else {
System.out.println(error);
}
//Get second char
System.out.println("Select an operator: & | ^");
userOperator = System.in.read();
if(userOperator==38) { // &
chosenOperator = 0;
} else if (userOperator==124) { // |
chosenOperator = 1;
} else if (userOperator==94) { // ^
chosenOperator = 2;
} else {
System.out.println(error);
}
//Get third char
System.out.println("Enter the second value:");
userChar2 = System.in.read();
System.in.close();
if((userChar2==84)||(userChar2==116)) {
b = true;
} else if ((userChar2==70)||(userChar2==102)) {
b = false;
} else {
System.out.println(error);
}
//Figure out result
boolean result;
switch (chosenOperator) {
case 0:
result = a&b;
case 1:
result = a|b;
case 2:
result = a^b;
System.out.println(result);
}
} catch(IOException e) {
}
}
执行此代码会使控制台在第一个System.in.read()
之后等待用户输入并使其正确检查char输入。然而,在此之后,所有后续System.in.read()
都将被忽略,程序将终止。
我找到了一段使用System.in.close()
的代码,因此在每System.in.read()
之后仍然不知道我拼接的方法到底是什么。这会导致程序在调用System.in.read()
后的第一个System.in.close()
时终止。
那么,到底发生了什么?您将如何正确使用System.in.read()
?
答案 0 :(得分:3)
问题不在于System.in.read(),而在于控制台。
控制台通常是缓冲的,这意味着只有在按下回车键后才能将数据发送到您的程序(因此可由System.in.read()读取)。
所以你必须将控制台切换到无缓冲模式,但没有可移植的方法来执行此操作,因为有太多不同类型的控制台(unix shell,cmd窗口,Eclipse控制台等)。
如果不允许使用除System.in.read()和System.out.println()方法之外的任何内容,则必须让用户在一行中输入完整的术语,按回车键,然后您可以处理这些字符输入,例如:
public static void main(String[] args) throws IOException {
boolean a = true; // char: 84 or 116 for T and t
boolean b = false; // char: 70 or 102 for F and f
int userChar1;
int userOperator;
int userChar2;
System.out.println("Please enter the term, e.g. T&F:");
userChar1 = System.in.read();
userOperator = System.in.read();
userChar2 = System.in.read();
a = userChar1 == 'T' || userChar1 == 't';
b = userChar2 == 'T' || userChar1 == 't';
switch (userOperator) {
case '&':
System.out.println(a & b);break;
case '|':
System.out.println(a | b);break;
case '^':
System.out.println(a ^ b);break;
default:
System.out.println("unknow operator");
}
}
答案 1 :(得分:1)
查看以下代码部分:
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
String input = null;
// read the input from the command-line; need to use try/catch with the
// readLine() method
try {
input = br.readLine();
} catch (IOException e) {
System.out.println("IO error trying to read your input!");
System.exit(1);
}
System.out.println("your input: "+input);
如果您不允许使用bufferReader,我请您查看bufferReader的源代码。
答案 2 :(得分:1)
就个人而言,我运行你的代码没有问题,但它有一些我必须研究的奇怪效果。
这种方法的主要问题(使用System.in.read()
)是当用户输入某个角色时,他必须按enter
,因此你有2个字符而不是你想要的1个 - 第一个用户输入的字符(我们假设,在您的情况下为T或F)和新行字符。
我设法让您的代码进行微小的更改。您需要调用read()
方法的重载版本 - read(byte[] b)
,其中包含some number of bytes from the input stream and stores them into the buffer array
。
以下是代码的第一部分,已修改:
byte[] input = new byte[10];
System.out.println("Enter the first value (T or F):");
System.in.read(input);
userChar1 = input[0];
if ((userChar1 == 84) || (userChar1 == 116)) { // T or t
a = true;
} else if ((userChar1 == 70) || (userChar1 == 102)) { // F or f
a = false;
} else {
System.out.println(error);
}
注意,我们不关心read()
返回什么,我们只关心来自input
数组的第一个char。其余的代码以相同的方式进行修改,您甚至可以使用相同的缓冲区数组(input
)并查询第0个元素。