There is currently a query program get_user_id is written in C, Python needs to call this program: Use get_user_id "username" can get output: "ID0002451". using a pipeline in Python makes it easy to invoke this process and get its standard output:get_user_id is written in C, the approximate framework of the program is as follows: Get a command-line argument, and then print its corresponding ID according to the parameters:
intMainintARGC,Char* args[])
{
Char* name = Args[1]
printf ("%s",GetID (name));
}
the fragments of the Python program call are as follows:pipe = Os.popen ( "get_user_id" + "myname")
user_id = Pipe.read () Pipe.close ()
This is how Python calls the GET_USER_ID program. First Python starts a subprocess, then reads the standard output of the child process and ends the child process. The main overhead here is the initiation and revocation of the process, and the communication between the pipelines is very fast. If the get_user_id call is not very frequent, then this method of invocation is not a problem, if the get_user_id is called very frequently, so that its performance becomes the bottleneck of the system, it is necessary to optimize. The optimization method is to make the get_user_id child process resident memory, the Python parent process can use Write/flush and ReadLine methods and child process communication, the end of the program to revoke the child process. after the process has resident memory, Python only needs to start a child process to satisfy any query. But the trouble is that the GET_USER_ID program needs rewriting: instead of receiving the standard input in the loop, the result is sent to the standard output, and a special input (such as "EOF") is specified, the child process exits the loop after receiving the input. get_user_id after the change
intMainintARGC,Char* args[])
{CharNAME[512]; Buff
while (scanf ("%s", name)) {if (!STRCMP (name, "EOF")) return 0;
printf ("%s\n",GetID (name)); }
}
this C program first accepts the standard input, determines whether the input ends as the end flag, or returns if it is, otherwise prints the user ID. How should python invoke this process? Pipe objects that are obtained using popen () only support write or read operations, but cannot read and write at the same time. you need to allow both read and write operations, using POPEN2 (). The function returns a tuple of two elements, which in turn is a write pipeline (which can write standard input to the target process) and a read pipeline (that is, the standard output of the read process). If you need to deal with the C program above, you should open the pipeline like thispipe_out, pipe_in = Popen2 ("get_user_id", "WR"); "WR" indicates that the secondary pipeline needs to be written and read first. specific examples are as follows: 10,000 queries Import OS
if__name__ = ="__main__":
pipe_in, pipe_out = Popen2 ("get_user_id","WR");
forIinchRange (10000)
Pipe_in.write ("myname");
Pipe_in.write ("\ n"); #需要换行符
Pipe_in.flush (); #需要清空缓冲区
userid = Pipe_out.readline (); #读入结果
It is important to note that in order to interact with the process smoothly, it is generally necessary to flush, prevent IO buffering, write and read the entire line as much as possible to control the pipeline interaction process. According to the author's experiment, the process of using resident memory to make 10,000 calls is much faster than the process of non-resident memory, the former consumes about 1/5 of the latter, but this result is only a special case of the author. Ask readers to analyze their applications and see how to use Python's powerful plumbing tools. Ps,python also has Popen3, which opens the Stdin,stdout and stderr of the process, better and more powerful. There is also a more powerful process management interface under the subprocess module.
How Python and other processes communicate in a pipeline--popen and popen2 comparisons