What is the difference between env, declare and compgen -v?

I see that printenv and env are giving the same output. When digging further for getting the complete list of environment variables, I found declare -xp and the command from here:

compgen -v | while read line; do echo $line=${!line};done

What are the differences between these commands in terms of environment variables.


The env command can run other commands with modified environments. If no command is given, env prints environment variables (i.e., exported variables). printenv can only print environment variables (it cannot run commands). See this U&L question for more differences between the two.

compgen -v outputs only names of all shell variables, exported or not. That's why you have to use variable indirection (${!line}) to get the value of the variable. compgen -v is typically used for tab completion.

declare -p prints details of the shell variables in a re-usable manner, typically in the form of more declare commands. The -x option restricts the output to exported variables. The output of declare can be eval'd later, to get back a given state of variables.

set can be used to set various shell options, or the positional parameters. If no arguments or options are given, then it prints all shell variables and functions.

export can be used to export variables or functions. With the -p option, it prints exported variables and functions.