int main(int argc, char *argv[], char *env[])
{
printf("Press any key to exit.\n");
getch();
return 0;
}
根据手册页,
getchshould wait until any key is pressed
...但实际上它在按任意键之前直接返回。 (返回值为-1)。
为什么?
更新
我在 Linux 上。如果不使用 getch(),我该如何实现 Press any key to exit.?
getchar() 只会在回车后返回,这不是我想要的。
最佳答案
在 Linux 上,getch() 可能是 curses 函数,它与 Windows 特定的同名函数有很大不同。 curses (ncurses) 对于您想做的事情来说可能有点矫枉过正。
最简单的方法是等到用户按下 Enter,您可以这样做:
int c;
printf("Press <enter> to quit: ");
fflush(stdout);
while ((c = getchar()) != '\n' && c != EOF) {
/* nothing */
}
如果您真的希望用户能够按任何键,而不仅仅是Enter,您可以这样做:
system("stty cbreak -echo");
getchar();
system("stty cooked echo");
第二个 stty 旨在将 tty 恢复到合理的设置(它应该真正将它们恢复到原来的状态,但保存和恢复状态有点复杂)。可能有更简洁的方法来做到这一点(使用 stty 程序本身使用的任何库函数)。
编辑: 无需等待 Enter 即可读取单个字符是一个常见问题。事实上,这是 comp.lang.c FAQ 中的问题 19.1。 .
EDIT2: 最近我没有对 curses 做太多工作,但我只是玩弄了一下。除非您先调用 initscr() 并且 initscr() 清除屏幕,否则 getch() 似乎不会工作。 curses 旨在用于需要完全控制显示的应用程序,如文本编辑器。可能有一种方法可以在不控制屏幕的情况下使用 getch(),但我还没有找到。
system("stty ...") 拼凑实际上可能是最好的方法。
EDIT3: 另一个答案中的 termios 解决方案可能是最好的 (system("stty ...") 更简单,但调用外部程序感觉有点矫枉过正。
至于 OP 的评论“我无法相信 Press any key to exit. is so troubles to do in c”,是的,这看起来确实很奇怪——但进一步思考有正当理由。
看看安装在典型 Unix 或 Linux 系统上的程序。我认为您会发现它们中很少有人需要这种输入(等待一次按键)。
许多程序使用命令行参数和从文件或 stdin 读取的数据。用户键入的任何内容都是输入数据,而不是命令或对提示的响应。
有些程序确实会要求对某些操作进行确认(apt-get 和 cpan 等安装程序经常这样做)——但它们通常会读取行 输入并检查第一个字符。或者,对于一些激烈的操作,他们可能会要求您键入整个单词“yes”,然后键入 Enter(您不想重新格式化硬盘,因为您不小心按下了一个键)。
当然有很多程序(文本编辑器、文件查看器)读取单字符非回显输入,但此类程序往往是基于 curses 的;他们控制整个终端窗口。
最后,许多程序都有 GUI 界面(网络浏览器等);他们可能甚至不从标准输入中读取数据。
大多数生产 Unix 程序不使用或不需要 Press any key to exit 提示。他们只是做他们的工作,通常是默默地,然后终止,这样你就可以做下一件事了。需求主要存在于相对初级的程序,例如家庭作业。并不是说家庭作业有什么问题,但整个系统的主要设计目的并不是支持这种用法。
关于c - 为什么 getch() 在按下任意键之前返回?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/7410447/
类classAprivatedeffooputs:fooendpublicdefbarputs:barendprivatedefzimputs:zimendprotecteddefdibputs:dibendendA的实例a=A.new测试a.foorescueputs:faila.barrescueputs:faila.zimrescueputs:faila.dibrescueputs:faila.gazrescueputs:fail测试输出failbarfailfailfail.发送测试[:foo,:bar,:zim,:dib,:gaz].each{|m|a.send(m)resc
我有一个模型:classItem项目有一个属性“商店”基于存储的值,我希望Item对象对特定方法具有不同的行为。Rails中是否有针对此的通用设计模式?如果方法中没有大的if-else语句,这是如何干净利落地完成的? 最佳答案 通常通过Single-TableInheritance. 关于ruby-on-rails-Rails-子类化模型的设计模式是什么?,我们在StackOverflow上找到一个类似的问题: https://stackoverflow.co
我正在使用的第三方API的文档状态:"[O]urAPIonlyacceptspaddedBase64encodedstrings."什么是“填充的Base64编码字符串”以及如何在Ruby中生成它们。下面的代码是我第一次尝试创建转换为Base64的JSON格式数据。xa=Base64.encode64(a.to_json) 最佳答案 他们说的padding其实就是Base64本身的一部分。它是末尾的“=”和“==”。Base64将3个字节的数据包编码为4个编码字符。所以如果你的输入数据有长度n和n%3=1=>"=="末尾用于填充n%
我主要使用Ruby来执行此操作,但到目前为止我的攻击计划如下:使用gemsrdf、rdf-rdfa和rdf-microdata或mida来解析给定任何URI的数据。我认为最好映射到像schema.org这样的统一模式,例如使用这个yaml文件,它试图描述数据词汇表和opengraph到schema.org之间的转换:#SchemaXtoschema.orgconversion#data-vocabularyDV:name:namestreet-address:streetAddressregion:addressRegionlocality:addressLocalityphoto:i
为什么4.1%2返回0.0999999999999996?但是4.2%2==0.2。 最佳答案 参见此处:WhatEveryProgrammerShouldKnowAboutFloating-PointArithmetic实数是无限的。计算机使用的位数有限(今天是32位、64位)。因此计算机进行的浮点运算不能代表所有的实数。0.1是这些数字之一。请注意,这不是与Ruby相关的问题,而是与所有编程语言相关的问题,因为它来自计算机表示实数的方式。 关于ruby-为什么4.1%2使用Ruby返
它不等于主线程的binding,这个toplevel作用域是什么?此作用域与主线程中的binding有何不同?>ruby-e'putsTOPLEVEL_BINDING===binding'false 最佳答案 事实是,TOPLEVEL_BINDING始终引用Binding的预定义全局实例,而Kernel#binding创建的新实例>Binding每次封装当前执行上下文。在顶层,它们都包含相同的绑定(bind),但它们不是同一个对象,您无法使用==或===测试它们的绑定(bind)相等性。putsTOPLEVEL_BINDINGput
我可以得到Infinity和NaNn=9.0/0#=>Infinityn.class#=>Floatm=0/0.0#=>NaNm.class#=>Float但是当我想直接访问Infinity或NaN时:Infinity#=>uninitializedconstantInfinity(NameError)NaN#=>uninitializedconstantNaN(NameError)什么是Infinity和NaN?它们是对象、关键字还是其他东西? 最佳答案 您看到打印为Infinity和NaN的只是Float类的两个特殊实例的字符串
如果您尝试在Ruby中的nil对象上调用方法,则会出现NoMethodError异常并显示消息:"undefinedmethod‘...’fornil:NilClass"然而,有一个tryRails中的方法,如果它被发送到一个nil对象,它只返回nil:require'rubygems'require'active_support/all'nil.try(:nonexisting_method)#noNoMethodErrorexceptionanymore那么try如何在内部工作以防止该异常? 最佳答案 像Ruby中的所有其他对象
关闭。这个问题需要detailsorclarity.它目前不接受答案。想改进这个问题吗?通过editingthispost添加细节并澄清问题.关闭8年前。Improvethisquestion为什么SecureRandom.uuid创建一个唯一的字符串?SecureRandom.uuid#=>"35cb4e30-54e1-49f9-b5ce-4134799eb2c0"SecureRandom.uuid方法创建的字符串从不重复?
我有一个服务模型/表及其注册表。在表单中,我几乎拥有服务的所有字段,但我想在验证服务对象之前自动设置其中一些值。示例:--服务Controller#创建Action:defcreate@service=Service.new@service_form=ServiceFormObject.new(@service)@service_form.validate(params[:service_form_object])and@service_form.saverespond_with(@service_form,location:admin_services_path)end在验证@ser