2012-03-12 132 views
0

我是Linux新手。我遇到这段代码来打印环境变量。这有点让我困惑。这个代码如何打印环境变量?在Linux中打印环境变量

#include <stdio.h> 

extern char **environ; 
int main() 
{ 
    char **var; 
    for(var=environ; *var!=NULL;++var) 
     printf("%s\n",*var); 

    return 0; 
} 

什么是extern在这里?

回答

1

如果你不知道什么意思是,请找一本书来学习C语言。它仅仅意味着'定义在其他地方,但在这里使用'。

这几天environ全局变量在<unistd.h>中声明(尽管很长一段时间没有声明它的头)。它就像程序中的argv数组,它是一个字符指针数组,每个指针都指向name=value格式的环境变量。该列表由空指针终止,如argv是。尽管如此,环境并不算数。

for (var = environ; *var != NULL; ++var) 
    printf("%s\n", *var); 

因此,在第一次迭代中,在第一环境变量var点;那么它会增加到下一个,直到值*var(a char *)为NULL,表示列表结束。

这个循环还可以写成:

char **var = environ; 
while (*var != 0) 
    puts(*var++); 
+0

为什么我们使用++变种?我们不能使用++ var – user1263375 2012-03-12 06:29:39

+0

在'for'循环代码中,'++ var'和'var ++'基本上是一样的。在'while'循环代码中,使用'* ++ var'会跳过第一个条目。还有,我称之为'al'(用于参数列表)相关的程序,它是像'echo'但每行打印其参数之一:'#包括 INT主(INT ARGC,字符**的argv){而(* ++ argv)puts(* argv);返回0; }'它使用'* ++ argv'而不是类似的'* var ++',因为它故意跳过程序名。 – 2012-03-12 09:06:38

1

维基百科http://en.wikipedia.org/wiki/External_variable

定义,声明和extern关键字

为了理解变量是如何外部涉及到extern关键字,它有必要了解定义和声明变量之间的区别。当一个变量被定义时,编译器会为该变量分配内存,并可能将其内容初始化为某个值。当声明变量时,编译器要求将变量定义在别处。该声明通知编译器,该名称和类型存在一个变量,但编译器不需要为它分配内存,因为它是在别处分配的。

extern关键字的意思是“不定义声明”。换句话说,它是一种显式声明变量的方法,或者在没有定义的情况下强制声明。也可以明确定义变量,即强制定义。它通过分配一个初始化值给一个变量来完成。如果extern关键字和初始化值都不存在,则该语句可以是声明或定义。由编译器来分析程序的模块并做出决定。

变量必须在程序的某个模块中定义一次。如果没有定义或多个定义,则可能在链接阶段产生错误。一个变量可以多次声明,只要声明彼此一致并且与定义(头文件大大方便)相一致即可。它可以在许多模块中声明,包括模块在哪里定义,甚至在同一个模块中多次。但是在模块中多次声明它通常是毫无意义的。

一个外部变量也可以在函数内声明。在这种情况下,必须使用extern关键字,否则编译器会认为它是局部变量的定义,它具有不同的作用域,生命周期和初始值。这个声明只会在函数内部而不是整个函数的模块中可见。

应用于函数原型的extern关键字绝对没有任何作用(应用于函数定义的extern关键字当然是非感性的)。一个函数原型总是一个声明而不是一个定义。另外,在ANSI C中,函数总是外部的,但是一些编译器扩展和更新的C标准允许函数在函数内部定义。

一个外部变量必须定义一次,超出任何 函数;这为它留出了存储空间。该变量还必须在每个想要访问它的函数中声明的 ;这说明变量的 类型。该声明可能是一个明确的extern 声明或可能从上下文隐含。 ...您应该注意,当我们将 引用到本节中的外部变量时,我们 正在仔细地使用单词定义和声明。定义是指 其中变量创建或分配存储的地方;声明将 指向变量性质的地方,但未分配存储空间 。

-The C程序设计语言

范围,寿命和static关键字

外部变量可以由所有的功能中的程序的所有模块进行访问。这是一个全局变量。为了能够使用该变量的函数,声明或外部变量的定义必须位于源代码中的函数定义之前。或者必须在函数内部使用关键字extern声明变量。

应用于外部变量定义的static关键字(static和extern是互斥的)会对此进行一点改变:变量只能由定义它的同一模块中的函数访问。但是,同一个模块中的函数可能会将该变量的引用(指针)传递给另一个模块中的另一个函数。在这种情况下,即使函数在另一个模块中,它也可以读取和修改变量的内容 - 它不能通过名称引用它。

也可以在定义局部变量时使用static关键字。如果没有static关键字,则在调用函数时自动分配变量,并在函数退出时释放该变量(因此名称为“自动变量”)。它的值不会在函数调用之间保留。使用static关键字时,该变量在程序启动时分配,并在程序结束时释放。它的值在函数调用之间不会丢失。该变量仍然是本地的,因为它只能在定义它的函数内通过名称访问。但是对它的引用(指针)可以传递给另一个函数,从而允许它读取和修改变量的内容(再次不用名称来引用它)。

当程序启动时会分配和初始化外部变量,并且仅在程序结束时释放内存。他们的一生和程序一样。

如果初始化没有明确完成,则将外部(静态或非静态)和本地静态变量初始化为零。本地自动变量未初始化,即包含“垃圾”值。

施加到一个函数定义静态关键字防止被称为按名称来自其模块外的函数(它仍然能够传递一个函数指针从模块中并用它来调用功能)。

实施例(C程序设计语言)

文件1:

int GlobalVariable;   // implicit definition 
    void SomeFunction();  // function prototype (declaration) 

    int main() { 
    GlobalVariable = 1; 
    SomeFunction(); 
    return 0; 
    } 

文件2:

extern int GlobalVariable; // explicit declaration 

    void SomeFunction() {  // function header (definition) 
    ++GlobalVariable; 
    } 

在这个例子中,可变全局变量在文件1中定义为了在文件2中使用相同的变量,它必须被声明。无论文件的数量如何,全局变量只定义一次,但是,它必须在包含定义的文件之外的任何文件中声明。

如果程序在多个源文件中,并且变量在file1中定义并在file2和file3中使用,则file2和file3中需要使用extern声明来连接变量的出现。通常的做法是在一个单独的文件中收集变量和函数的extern声明,这个文件历史上称为头文件,包含在每个源文件前面的#include中。后缀.h对于标题名称是常规的。

0

的extern字符** ENVIRON;

的变量environ来自你的图书馆,你会链接。

该变量保存了您当前的系统环境变量

linux系统。这就是为什么你可以这样做。