xcode 使用 popen() 在命令行中打开程序?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/6088913/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-14 21:05:47  来源:igfitidea点击:

Using popen() to open a program in command line?

cxcodecommand-linepopen

提问by Mike

Is it possible to open a program using another program? For example: I want to make a command line application in C that will prompt the user to type in the name of a program (lets say Microsoft Word.app), and that program will launch. Would I do something like this:

是否可以使用另一个程序打开一个程序?例如:我想用 C 制作一个命令行应用程序,它会提示用户输入程序的名称(比如 Microsoft Word.app),然后该程序将启动。我会做这样的事情:

#include <stdio.h>
#include <time.h>
int main (int argc, const char * argv[]) {
    char programName[1000];
    printf("Type in the name of the program you would like to open: ");
    scanf("%s", programName);
    popen(programName);
}

However, popen() asks me for another char. How would I go about using popen() to open the program?

但是, popen() 要求我输入另一个字符。我将如何使用 popen() 打开程序?

EDIT: The following code works!

编辑:以下代码有效!

#include <stdio.h>
#include <time.h>

int main (int argc, const char * argv[]) {
    char programName[1000];
    char app[100] = ".app";
    char openApp[100] = "open /Applications/";
    printf("Type in the name of the program you would like to open: ");
    scanf("%s", programName);
    strcat(openApp, programName);
    strcat(openApp, app);
    system(openApp);

}

回答by zneak

popenlets you launch a program and get a file descriptor to its input or output, much like fopenworks for files. For instance, if you wanted to read the output of your program, you'd use popen("program", "r"). On the other hand, if you want to write to its input, you would use popen("program", "w"). Mac OS X also allows for r+, which lets you read the output and write to the input but this capability isn't standard and shouldn't be relied on for cross-platform code.

popen允许你启动一个程序并获得一个文件描述符到它的输入或输出,就像fopen文件一样。例如,如果您想读取程序的输出,您可以使用popen("program", "r"). 另一方面,如果您想写入其输入,则可以使用popen("program", "w"). Mac OS X 还允许r+,它允许您读取输出并写入输入,但此功能不是标准功能,不应依赖跨平台代码。

If you just want to launch a program, you might as well use the systemfunction, which does that and waits until the program exits, at which point it returns the status code. systemactually invokes the shell to work, so arguments will undergo expansion (environment variables, ~, etc).

如果您只想启动一个程序,您不妨使用该system函数,它会执行此操作并等待程序退出,此时它会返回状态代码。system实际上调用 shell 来工作,因此参数将进行扩展(环境变量、~ 等)。

EDITFollowing your comment that system("Microsoft Word.app")doesn't work as you'd expect: there are several reasons for this, actually. Starting with the message you get: this is because what you wrote is equivalent to opening a terminal window and typing Microsoft Word.app. In other words, it tries to find a program called "Microsoft", then pass it the argument "Word.app". You would need to either quote the program name or escape spaces to have the shell understand it's a whole program name and not a program name then an argument: system("Microsoft\ Word.app")

编辑按照您的评论system("Microsoft Word.app")并不如您所愿:实际上有几个原因。从你得到的消息开始:这是因为你写的内容相当于打开一个终端窗口并输入Microsoft Word.app. 换句话说,它试图找到一个名为“Microsoft”的程序,然后将参数“Word.app”传递给它。您需要引用程序名称或转义空格以使外壳程序理解它是整个程序名称而不是程序名称,然后是参数:system("Microsoft\ Word.app")

Now, this should complain saying that the shell can't find the program "Microsoft Word.app", which is already a step forward.

现在,这应该抱怨说 shell 找不到程序“Microsoft Word.app”,这已经向前迈进了一步。

This is because on Mac OS, appfiles aren't executable files: they're folders that the Finder displays as a single file. You can verify that by ctrl+clicking (or right-clicking) an app and selecting "Show package contents" (this will open the app folder). The actual executable for Microsoft Word.app must be somewhere along the path of Microsoft Word.app/Contents/MacOS/Microsoft Word.

这是因为在 Mac OS 上,app文件不是可执行文件:它们是 Finder 显示为单个文件的文件夹。您可以通过 ctrl+单击(或右键单击)应用程序并选择“显示包内容”(这将打开应用程序文件夹)来验证这一点。Microsoft Word.app 的实际可执行文件必须位于Microsoft Word.app/Contents/MacOS/Microsoft Word.

As you can see, this is getting kind of complex. Luckily enough, Apple provides the openexecutable, which can use a bunch of OS services to figure out those details. It allows to launch applications in the following fashion:

如您所见,这变得有点复杂。幸运的是,Apple 提供了open可执行文件,它可以使用一堆操作系统服务来找出这些细节。它允许以下列方式启动应用程序:

open -a Microsoft\ Word

This should launch Word. (Notice how you stillneed to escape the spaces.) In pure C code, that would get you something like this:

这应该会启动 Word。(注意你仍然需要如何转义空格。)在纯 C 代码中,这会让你得到这样的东西:

system("open -a Microsoft\ Word");

If you choose to use Objective-C and Cocoa, however, there is a very simple way to open applications:

但是,如果您选择使用 Objective-C 和 Cocoa,则有一种非常简单的方法可以打开应用程序:

NSString* appName = @"Microsoft Word"; // no escape!
[[NSWorkspace sharedWorkspace] launchApplication:appName];

NSStringobjects can be created from C string easily enough:

NSString可以很容易地从 C 字符串创建对象:

NSString* appName = [[NSString alloc] initWithCString:programName encoding:NSUTF8StringEncoding];
[[NSWorkspace sharedWorkspace] launchApplication:appName];
[appName release];

回答by DigitalRoss

It would be better to use system(3)for this purpose.

最好system(3)用于此目的。

The popen(3)function establishes a pipeline that can be read or written by the caller. But GUI applications do not use standard input and standard output, they connect to the graphical interface server, sometimes called the "window server".This server is already running and already has decided what its keyboard input will be, and it is always writing its output to the video device.

popen(3)函数建立了一个可由调用者读取或写入的管道。但是 GUI 应用程序不使用标准输入和标准输出,它们连接到图形界面服务器,有时称为“窗口服务器”。这个服务器已经在运行并且已经决定了它的键盘输入是什么,它总是将它的输出写入视频设备。

To start a .appyou should actually run the open(1)program, so try something like:

要启动.app,您实际上应该运行open(1)程序,因此请尝试以下操作:

system("open /Applications/MacVim.app");