විධාන රේඛාවේ පරිසර විචල්‍යයක් සකසා එය විධානවල දිස්වන්නේ කෙසේද?


179

මම දුවනවා නම්

export TEST=foo
echo $TEST

එය foo ප්‍රතිදානය කරයි.

මම දුවනවා නම්

TEST=foo echo $TEST

එය එසේ නොවේ. අපනයනය හෝ ස්ක්‍රිප්ට් භාවිතා නොකර මෙම ක්‍රියාකාරිත්වය ලබා ගන්නේ කෙසේද?


පරිස්සමින්, මෙම කතාවට මුලින් පෙනෙනවාට වඩා බොහෝ දේ ඇත. මගේ පිළිතුර පරීක්ෂා කිරීමට මම ඔබට ආරාධනා කරමි.
jasonleonhard

Answers:


214

මෙයට හේතුව ෂෙල් එක විධාන රේඛාවේ විචල්‍යය සැබවින්ම විධාන ක්‍රියාත්මක කිරීමට පෙර පුළුල් වන අතර එම අවස්ථාවේ විචල්‍යය නොපවතී. ඔබ භාවිතා කරන්නේ නම්

TEST=foo; echo $TEST

එය ක්‍රියාත්මක වනු ඇත.

exportපසුව ක්‍රියාත්මක කරන ලද විධාන වල පරිසරය තුළ විචල්‍යය දිස්වනු ඇත (මෙය බාෂ් තුළ ක්‍රියා කරන ආකාරය බලන්න help export). එක් විධානයක පරිසරය තුළ දර්ශනය වීමට ඔබට අවශ්‍ය වන්නේ විචල්‍යය නම්, ඔබ උත්සාහ කළ දේ භාවිතා කරන්න, එනම්:

TEST=foo your-application

1
/ Usr / bin / env ගැන කුමක් කිව හැකිද? ඒකත් වැඩ කරන්නේ නැහැ, ඇයි කියලා ඔයා දන්නවාද?
බෙනබර්ඩ්

7
එකම හේතුව - $TESTවිධාන රේඛාව ක්‍රියාත්මක කිරීමට පෙර කවචය පුළුල් වේ. ක්‍රියාත්මක වූ පසු echo( echoසාමාන්‍යයෙන් ෂෙල් බිල්ට්-විධාන වෙත පරිවර්ථනය වන අතර /bin/echoඑය එසේ නොවේ ) එය එහි පරිසරයේ විචල්‍ය කට්ටලය දකී. කෙසේ වෙතත්, විචල්‍යයේ අන්තර්ගතය එහි පරිසරයෙන් ප්‍රතිදානය කිරීමට echo $TESTනොකියයි . එය හැඳින්වෙන්නේ විචල්‍යයේ පවතින ඕනෑම දෙයක් තර්කය සමඟ ධාවනය වන ලෙසට ෂෙල්ට පවසන අතර ඒවා එකිනෙකට වෙනස් කරුණු දෙකකි. echoTESTechoTEST
පීටර්

terpeterph විධානය ක්‍රියාත්මක කිරීමට පෙර විධාන රේඛාවේ විචල්‍යය කවචය විස්තාරණය කරන්නේ නම් එය පුළුල් නොකරන්නේ var=value sh -c 'echo "$var"'ඇයි?
21:56 ට හැක්

1
මා ඔබට මෙහි පැහැදිලි කළ පරිදි : එයට හේතුව විචල්‍යයන් ද්විත්ව උපුටා දැක්වීම් (උදා:) තුළ පුළුල් වන "… $var …"නමුත් තනි උපුටා දැක්වීම් තුළ නොවේ (උදා. '… $var …'). echo "$var"තනි උපුටා දැක්වීම් තුළ ඇති බැවින් sh -c, පිටත, අන්තර්ක්‍රියාකාරී කවචය මගින් අර්ථ නිරූපණය නොකර එම සම්පූර්ණ නූල නව ( ) කවචයට ලැබෙනු ඇත. … (ඉදිරියට)
ජී-මෑන් පවසන්නේ මොනිකා නැවත

(Cont'd)… ඊගල් ඊයේ පැවසූ පරිදි , විග්‍රහ කිරීමේ වට දෙකක් තිබේ - මම විශ්වාස කළත්, igal ඔබේ ප්‍රශ්නය වැරදියට කියවා ඇති බව. මව් කවචය මඟින් සිදුකරන විග්‍රහයට අමතරව විග්‍රහ කිරීමේ වට දෙකක් නොමැත . විග්‍රහ කිරීමේ වට දෙකක් ඇත - එකක් පිටත, අන්තර්ක්‍රියාකාරී (මව්) කවචය මගින් ද, එකක් නව ( sh -c) ළමා කවචයෙන් ද සිදු කෙරේ.
ජී-මෑන් පවසන්නේ 'මොනිකා නැවත

43

පරිසර විචල්‍යයන්ට වඩා සීමිත විෂය පථයක් ලබා ගැනීමට ඔබට ෂෙල් විචල්‍යයන් තිබිය යුතු යැයි මම සැක කරමි . ඔවුන් විට පරිසරය විචල්ය විධානයන් සම්මත නූල් ලැයිස්තුවක් වේ ක්රියාත්මක .

තුළ

var=value echo whatever

ඔබ var=valueදෝංකාරය ලැබෙන පරිසරයට නූල් යවනවා. කෙසේ වෙතත්, echoඑහි පරිසර ලැයිස්තුව සමඟ කිසිවක් නොකරන්න - කෙසේ වෙතත් බොහෝ ෂෙල් වෙඩි තුළ echoඑය ඉදිකර ඇති අතර එබැවින් ක්‍රියාත්මක නොවේ .

ඔබ ලියා ඇත්නම්

var=value sh -c 'echo "$var"'

එය තවත් කාරණයක් වනු ඇත. මෙන්න, අපි විධානය var=valueවෙත යමු, එහි පරිසරය භාවිතා කිරීම සිදු වේ. ෂෙල් වෙඩි ඔවුන්ගේ පරිසරයෙන් ලැබෙන සෑම විචල්‍යයක්ම ෂෙල් විචල්‍යයක් බවට පරිවර්තනය කරයි , එබැවින් ලැබෙන පරිසර විචල්‍යය විචල්‍යයක් බවට පරිවර්තනය වන අතර එය එම විධාන රේඛාව තුළ එය පුළුල් කළ විට එය බවට පත්වේ . පරිසරය පෙරනිමියෙන් උරුම වී ඇති නිසා, එහි පරිසරය තුළ ද ලැබෙනු ඇත (නැතහොත් එය ක්‍රියාත්මක කරනු ලැබුවේ නම්), නමුත් නැවතත්, පරිසරය ගැන තැකීමක් නොකරයි.shshvarsh$varechoecho valueechovar=valueecho

දැන්, මා සැක කරන පරිදි, ඔබට අවශ්‍ය වන්නේ ෂෙල් විචල්‍යයන්ගේ විෂය පථය සීමා කිරීමයි, හැකි ප්‍රවේශයන් කිහිපයක් තිබේ.

අතේ ගෙන යා හැකි (බෝර්න් සහ පොසික්ස්):

(var=value; echo "1: $var"); echo "2: $var"

ඉහත (...) උප කවචයක් (බොහෝ ෂෙල් වෙඩි වල නව ෂෙල් ක්‍රියාවලියක්) ආරම්භ කරයි, එබැවින් එහි ප්‍රකාශිත ඕනෑම විචල්‍යයක් එම උප කවචයට පමණක් බලපානු ඇත, එබැවින් ඉහත කේතය "1: අගය" ප්‍රතිදානය කරනු ඇතැයි මම අපේක්ෂා කරමි. සහ "2:" හෝ "2: කුමක් වුවත්-පෙර-සකසා තිබුනේ".

බොහෝ බෝර්න් වැනි ෂෙල් වෙඩි සමඟ, ඔබට කාර්යයන් සහ "දේශීය" බිල්ඩින් භාවිතා කළ හැකිය:

f() {
  local var
  var=value
  echo "1: $var"
}
f
echo "2: $var"

Zsh සමඟ, ඔබට පේළිගත කිරීමේ කාර්යයන් භාවිතා කළ හැකිය:

(){ local var=value; echo "1: $var"; }; echo "2: $var"

හෝ:

function { local var=value; echo "1: $var"; }; echo "2: $var"

Bash සහ zsh සමඟ (නමුත් අළු, pdksh හෝ AT&T ksh නොවේ), මෙම උපක්‍රමයද ක්‍රියාත්මක වේ:

var=value eval 'echo "1: $var"'; echo "2: $var"

ඒ ප්රභේද්යයක් වඩා ෂෙල් වෙඩි කිහිපයක් කෘති (එම dash, mksh, yash) නමුත් zsh(දී මිස sh/ kshරූප රචනයක්):

var=value command eval 'echo "1: $var"'; echo "2: $var"

( POSIX කවච commandවල ඇති විශේෂ බිල්ඩින් ඉදිරිපිට (මෙහි eval) භාවිතා කිරීමෙන් ඒවායේ විශේෂත්වය ඉවත් වේ (මෙහිදී ඔවුන්ගෙන් විචල්‍ය පැවරුම් නැවත පැමිණි පසු ක්‍රියාත්මක වේ))


Rick තදින් කිවහොත් එය සම්පූර්ණයෙන්ම සත්‍ය නොවේ. නිර්මාණයන් කිහිපයක් ස්ථානගත පරිසරය විචල්යයන් (ගැන සැලකිලිමත් වනු ඇත LANG, LOCPATH, LC_*...), ඒ ගැන යනු GNU ක්රියාත්මක සැළකිලිමත් වන POSIXLY_CORRECTපරිසර විචල්ය (සංසන්දනය env echo --versionසමග POSIXLY_CORRECT=1 env echo --versionවූ GNU පද්ධතිය මත).


මගේ අරමුණු සඳහා, මෙය නිවැරදි විසඳුමයි. 'Var' විචල්‍යය පිළිගත් පිළිතුරෙහි මෙන් පරිසරය දූෂණය කිරීමට මට අවශ්‍ය නැත.
kronenpj

10

ඔබ එය නිවැරදිව කරනවා, නමුත් බාෂ් සින්ටැක්ස් වැරදි ලෙස අර්ථ නිරූපණය කිරීම පහසුය: ඔබට සිතිය හැකිය env var ලබා ගැනීමට echo $TESTහේතු වන echoඅතර TESTපසුව එය මුද්‍රණය කරන්න, එය එසේ නොවේ. එසේ ලබා දී ඇත

export TEST=123

එවිට

TEST=456 echo $TEST

පහත දැක්වෙන අනුක්‍රමය ඇතුළත් වේ:

  1. කවචය මුළු විධාන රේඛාව විග්‍රහ කර සියලු විචල්‍ය ආදේශක ක්‍රියාත්මක කරයි, එබැවින් විධාන රේඛාව බවට පත්වේ

    TEST=456 echo 123
  2. එය විධානයට පෙර සැකසූ තාවකාලික වර්ස් නිර්මාණය කරයි, එබැවින් එය වත්මන් අගය සුරකින අතර TESTඑය 456 සමඟ නැවත ලියයි; විධාන රේඛාව දැන්

    echo 123
  3. එය ඉතිරි විධානය ක්‍රියාත්මක කරයි, මේ අවස්ථාවේ දී 123 සිට stdout දක්වා මුද්‍රණය කරයි (එබැවින් ඉතිරිව ඇති shell විධානයෙහි තාවකාලික අගය පවා භාවිතා නොකරයි TEST)

  4. එහි වටිනාකම යථා තත්වයට පත් කරයි TEST

විචල්ය ආදේශනයකට සම්බන්ධ නොවන බැවින් ඒ වෙනුවට printenv භාවිතා කරන්න:

>> export TEST=123
>> printenv TEST
123
>> TEST=456 printenv TEST
456
>> printenv TEST && TEST=456 printenv TEST && TEST=789 printenv TEST && printenv TEST
123
456
789
123
>>

+1 printenvසංකල්පය පරීක්ෂා කිරීමට / ඔප්පු කිරීමට මට ප්‍රයෝජනවත් විය (පිටපතක් මෙන් හැසිරේ, ඊට වෙනස්ව echo)
ඩැරින්

5

මෙය භාවිතා කිරීමෙන් ඔබට මෙය ලබා ගත හැකිය:

TEST=foo && echo $TEST

6
මෙම අවස්ථාවේ දී, TEST=fooවෙනම ප්‍රකාශයක් ලෙස ක්‍රියාත්මක වේ - එය සන්දර්භය තුළ පමණක් සකසා නැත echo.
codeforester
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.