في شل ماذا يفعل "2>&1" يعني ؟
سؤال
في Unix shell, إذا كنت ترغب في الجمع بين stderr
و stdout
في stdout
تيار لمزيد من التلاعب أستطيع إلحاق التالية في نهاية الأمر:
2>&1
لذلك, إذا كنت ترغب في استخدام head
على الإخراج من g++
, أنا يمكن أن تفعل شيئا مثل هذا:
g++ lots_of_errors 2>&1 | head
حتى أستطيع أن أرى الأولى فقط قليل من الأخطاء.
لدي دائما مشكلة في تذكر هذا, و لدي باستمرار أن تذهب للبحث عنه, و هو أساسا لأنني لا أفهم تماما جملة من هذه الخدعة خاصة.
يمكن أن أحدهم كسر هذا شرح حرف ما 2>&1
يعني ذلك ؟
المحلول
واصف ملف 1 هو الإخراج القياسي (stdout
).
واصف ملف 2 هو الخطأ المعياري (stderr
).
وهنا هو واحد طريقة لتذكر هذا البناء (على الرغم من أنها ليست دقيقة تماما): في البداية، 2>1
قد تبدو طريقة جيدة لإعادة توجيه stderr
إلى stdout
. ومع ذلك، فإن الواقع أن تفسر بأنها "stderr
إعادة توجيه إلى 1
ملف اسمه". &
يشير إلى أن ما يلي هو واصف الملف وليس اسم الملف. بحيث يصبح بناء: 2>&1
نصائح أخرى
echo test > afile.txt
والموجهات المعياري لafile.txt
. هذا هو نفس فعل
echo test 1> afile.txt
لإعادة توجيه ستدير، يمكنك القيام به:
echo test 2> afile.txt
و>&
هو بناء الجملة لإعادة توجيه تيار اصف ملف آخر - 0 غير ستدين، 1 غير المعياري، و2 غير ستدير
ويمكنك إعادة توجيه المعياري لستدير عن طريق القيام:
echo test 1>&2 # or echo test >&2
وأو العكس بالعكس:
echo test 2>&1
وهكذا، وباختصار ... 2>
الموجهات ستدير إلى ملف (غير محدد)، إلحاق &1
الموجهات ستدير إلى المعياري.
بعض الحيل عن إعادة توجيه
بعض بناء الجملة خصوصية حول هذا قد يكون أهم السلوكيات.هناك بعض العينات عن إعادة توجيه ، STDERR
, STDOUT
, و الحجج يأمر.
1 - الكتابة أو إلحاق?
الرمز >
يعني إعادة توجيه.
>
يعني إرسال ككل الانتهاء من الملف, الكتابة فوق الهدف إذا وجدت (انظرnoclobber
باش ميزة في #3 في وقت لاحق).>>
يعني إرسال بالإضافة إلى من شأنه إلحاق الهدف إذا كان موجودا.
في أي حال, هل يمكن إنشاء الملف لو أنها غير موجودة.
2 - شل سطر الأوامر هو أمر يعتمد!!
لاختبار هذا ، نحن بحاجة أمر بسيط والتي سوف ترسل شيئا على كل النواتج:
$ ls -ld /tmp /tnt
ls: cannot access /tnt: No such file or directory
drwxrwxrwt 118 root root 196608 Jan 7 11:49 /tmp
$ ls -ld /tmp /tnt >/dev/null
ls: cannot access /tnt: No such file or directory
$ ls -ld /tmp /tnt 2>/dev/null
drwxrwxrwt 118 root root 196608 Jan 7 11:49 /tmp
(أتوقع أنك لا تملك دليل اسمه /tnt
, بالطبع ;).حسنا, لدينا!!
لذا دعونا نرى:
$ ls -ld /tmp /tnt >/dev/null
ls: cannot access /tnt: No such file or directory
$ ls -ld /tmp /tnt >/dev/null 2>&1
$ ls -ld /tmp /tnt 2>&1 >/dev/null
ls: cannot access /tnt: No such file or directory
آخر سطر الأوامر مقالب STDERR
إلى وحدة التحكم ، فإنه لا يبدو أن يكون السلوك المتوقع...ولكن...
إذا كنت تريد أن تجعل بعض بعد تصفية عن إخراج واحد ، أخرى أو كليهما:
$ ls -ld /tmp /tnt | sed 's/^.*$/<-- & --->/'
ls: cannot access /tnt: No such file or directory
<-- drwxrwxrwt 118 root root 196608 Jan 7 12:02 /tmp --->
$ ls -ld /tmp /tnt 2>&1 | sed 's/^.*$/<-- & --->/'
<-- ls: cannot access /tnt: No such file or directory --->
<-- drwxrwxrwt 118 root root 196608 Jan 7 12:02 /tmp --->
$ ls -ld /tmp /tnt >/dev/null | sed 's/^.*$/<-- & --->/'
ls: cannot access /tnt: No such file or directory
$ ls -ld /tmp /tnt >/dev/null 2>&1 | sed 's/^.*$/<-- & --->/'
$ ls -ld /tmp /tnt 2>&1 >/dev/null | sed 's/^.*$/<-- & --->/'
<-- ls: cannot access /tnt: No such file or directory --->
لاحظ أن آخر سطر الأوامر في هذه الفقرة هو نفسه تماما كما في الفقرة السابقة ، حيث كتبت لا يبدو أن يكون السلوك المتوقع (حتى هذا يمكن أن يكون حتى توقع السلوك).
حسنا, هناك القليل من الحيل عن إعادة توجيه ، فعل مختلفة العملية على كل النواتج:
$ ( ls -ld /tmp /tnt | sed 's/^/O: /' >&9 ) 9>&2 2>&1 | sed 's/^/E: /'
O: drwxrwxrwt 118 root root 196608 Jan 7 12:13 /tmp
E: ls: cannot access /tnt: No such file or directory
الملاحظه: &9
واصف يمكن أن يحدث تلقائيا بسبب ) 9>&2
.
إضافة:الملاحظه! مع الإصدار الجديد من باش (>4.0
) هناك ميزة جديدة و أكثر مثير الجملة من أجل القيام بهذا النوع من الأشياء:
$ ls -ld /tmp /tnt 2> >(sed 's/^/E: /') > >(sed 's/^/O: /')
O: drwxrwxrwt 17 root root 28672 Nov 5 23:00 /tmp
E: ls: cannot access /tnt: No such file or directory
وأخيرا هذه المتتالية التنسيق الإخراج:
$ ((ls -ld /tmp /tnt |sed 's/^/O: /' >&9 ) 2>&1 |sed 's/^/E: /') 9>&1| cat -n
1 O: drwxrwxrwt 118 root root 196608 Jan 7 12:29 /tmp
2 E: ls: cannot access /tnt: No such file or directory
إضافة:الملاحظه! نفس الجملة الجديد, في كلا الاتجاهين:
$ cat -n <(ls -ld /tmp /tnt 2> >(sed 's/^/E: /') > >(sed 's/^/O: /'))
1 O: drwxrwxrwt 17 root root 28672 Nov 5 23:00 /tmp
2 E: ls: cannot access /tnt: No such file or directory
حيث STDOUT
تذهب من خلال مرشح معين ، STDERR
إلى آخر وأخيرا كل النواتج دمج تذهب من خلال أمر ثالث مرشح.
3 - كلمة عن noclobber
الخيار >|
بناء الجملة
هذا عن الكتابة:
في حين set -o noclobber
إرشاد باش إلى لا الكتابة فوق أي ملف موجود ، >|
جملة يسمح لك بالمرور من خلال هذا القيد:
$ testfile=$(mktemp /tmp/testNoClobberDate-XXXXXX)
$ date > $testfile ; cat $testfile
Mon Jan 7 13:18:15 CET 2013
$ date > $testfile ; cat $testfile
Mon Jan 7 13:18:19 CET 2013
$ date > $testfile ; cat $testfile
Mon Jan 7 13:18:21 CET 2013
الكتابة فوق الملف في كل مرة ، حسنا الآن:
$ set -o noclobber
$ date > $testfile ; cat $testfile
bash: /tmp/testNoClobberDate-WW1xi9: cannot overwrite existing file
Mon Jan 7 13:18:21 CET 2013
$ date > $testfile ; cat $testfile
bash: /tmp/testNoClobberDate-WW1xi9: cannot overwrite existing file
Mon Jan 7 13:18:21 CET 2013
تمر من خلال مع >|
:
$ date >| $testfile ; cat $testfile
Mon Jan 7 13:18:58 CET 2013
$ date >| $testfile ; cat $testfile
Mon Jan 7 13:19:01 CET 2013
Unsetting هذا الخيار و/أو تستفسر إذا وضعت بالفعل.
$ set -o | grep noclobber
noclobber on
$ set +o noclobber
$ set -o | grep noclobber
noclobber off
$ date > $testfile ; cat $testfile
Mon Jan 7 13:24:27 CET 2013
$ rm $testfile
4 - الماضي أكثر من خدعة...
إعادة توجيه سواء الإخراج من الأمر ، ونحن نرى أن الحق جملة يمكن أن تكون:
$ ls -ld /tmp /tnt >/dev/null 2>&1
هذا خاصة الحالة هناك اختصار الجملة: &>
...أو >&
$ ls -ld /tmp /tnt &>/dev/null
$ ls -ld /tmp /tnt >&/dev/null
الملاحظه:إذا 2>&1
موجودة ، 1>&2
هو بناء الجملة الصحيح أيضا:
$ ls -ld /tmp /tnt 2>/dev/null 1>&2
4 - الآن سوف تمكنك من التفكير:
$ ls -ld /tmp /tnt 2>&1 1>&2 | sed -e s/^/++/
++/bin/ls: cannot access /tnt: No such file or directory
++drwxrwxrwt 193 root root 196608 Feb 9 11:08 /tmp/
$ ls -ld /tmp /tnt 1>&2 2>&1 | sed -e s/^/++/
/bin/ls: cannot access /tnt: No such file or directory
drwxrwxrwt 193 root root 196608 Feb 9 11:08 /tmp/
4c - إذا كنت مهتما في المزيد المعلومات
يمكنك قراءة دليل على ما يرام من خلال ضرب:
man -Len -Pless\ +/^REDIRECTION bash
في باش وحدة التحكم ;-)
لقد وجدت هذه الوظيفة الرائعة على إعادة توجيه: كل شيء عن إعادة توجيه
إعادة توجيه كل من الإخراج القياسي والخطأ المعياري إلى ملف
$ command &>الملف
هذا واحد يستخدم بطانة &>
المشغل إلى إعادة توجيه كل من إخراج تيارات - المعياري و stderr - من الأوامر إلى ملف.هذا هو باش اختصار بسرعة إعادة توجيه كل تيارات إلى نفس الوجهة.
هنا هو كيف اصف الملف الجدول يبدو بعد باش وقد توجيه كل تيارات:
كما ترون, كل المعياري و stderr الآن نقطة file
.لذلك أي شيء مكتوب إلى المعياري و stderr يحصل كتبت file
.
هناك عدة طرق لإعادة توجيه كل تيارات إلى نفس الوجهة.يمكنك إعادة توجيه كل تيار واحد بعد آخر:
الأمر $ >الملف 2>&1
هذا هو أكثر شيوعا طريقة لإعادة توجيه كل تيارات إلى ملف.أولا المعياري هو توجيهك إلى ملف ثم stderr تتكرر نفسه المعياري.لذلك كل تيارات نهاية المطاف مشيرا إلى file
.
عندما باش يرى العديد من توجيه ذلك العمليات من اليسار إلى اليمين.دعونا نذهب من خلال الخطوات و انظر كيف يحدث ذلك.قبل تشغيل أي أوامر باش ملف جدول واصف يبدو مثل هذا:
الآن باش العمليات الأولى إعادة التوجيه >الملف.لقد رأينا ذلك من قبل و يجعل المعياري أشر إلى الملف:
القادم باش يرى الثاني توجيه 2>&1.لم نر هذا التوجيه من قبل.هذه التكرارات ملف واصف 2 أن يكون نسخة من ملف واصف 1 نحصل على:
كل تيارات تم توجيهك إلى الملف.
ومع ذلك كن حذرا هنا!الكتابة
الأمر >الملف 2>&1
ليس هو نفسه كما في الكتابة:
الأمر $ 2>&1 >الملف
ترتيب إعادة توجيه المسائل باش!هذا الأمر الموجهات فقط مستوى الإخراج إلى ملف.على stderr لا تزال الطباعة إلى المحطة.أن نفهم لماذا يحدث ذلك ، دعنا نذهب من خلال الخطوات مرة أخرى.حتى قبل تشغيل الأمر, الملف جدول واصف يبدو مثل هذا:
الآن باش عمليات إعادة توجيه اليسار إلى اليمين.لأول مرة يرى 2>&1 لذلك التكرارات stderr إلى المعياري.ملف جدول واصف يصبح:
الآن باش يرى الثاني إعادة توجيه ، >file
, و إعادة توجيه المعياري إلى الملف:
هل ترى ماذا يحدث هنا ؟ Stdout الآن يشير إلى الملف ، ولكن stderr لا يزال يشير إلى المحطة!كل ما يحصل كتبت إلى stderr لا يزال يحصل طباعتها على الشاشة!لذا كن حذرا جدا مع النظام من الموجهات!
لاحظ أيضا أنه في باش, الكتابة
$ command &>الملف
هو بالضبط نفس:
الأمر $ >&file
الأرقام تشير إلى الملف واصفات (fd).
- صفر
stdin
- واحد هو
stdout
- اثنين
stderr
2>&1
الموجهات fd 2 إلى 1.
هذا يعمل من أجل أي عدد من واصفات الملفات إذا كان البرنامج يستخدم لهم.
يمكنك أن تبحث في /usr/include/unistd.h
إذا كنت قد نسيت لهم:
/* Standard file descriptors. */
#define STDIN_FILENO 0 /* Standard input. */
#define STDOUT_FILENO 1 /* Standard output. */
#define STDERR_FILENO 2 /* Standard error output. */
وقال أن كنت قد كتبت ج الأدوات التي تستخدم غير معيار واصفات الملف مخصص تسجيل الدخول إذا كنت لا أرى ذلك إلا إذا كنت إعادة توجيه إلى ملف أو شيء من هذا.
وهذا بناء يرسل تيار الخطأ المعياري (stderr
) إلى <م> الحالي م> موقع الإخراج القياسي (stdout
) - تظهر هذه قضية العملة قد أهملت من قبل إجابات أخرى
ويمكنك إعادة توجيه أي مقبض الإخراج إلى آخر باستخدام هذه الطريقة لكنها غالبا ما تستخدم لقناة stdout
وstderr
تيارات في تيار واحد للمعالجة.
وبعض الأمثلة على ذلك:
# Look for ERROR string in both stdout and stderr.
foo 2>&1 | grep ERROR
# Run the less pager without stderr screwing up the output.
foo 2>&1 | less
# Send stdout/err to file (with append) and terminal.
foo 2>&1 |tee /dev/tty >>outfile
# Send stderr to normal location and stdout to file.
foo >outfile1 2>&1 >outfile2
لاحظ أن هذا الأخير سوف <م> لا م> stderr
مباشرة إلى outfile2
- أنه الموجهات إلى ما stdout
كان عندما واجه الحجة (outfile1
) و <م> ثم م> الموجهات stdout
إلى outfile2
.
وهذا يسمح بعض الخداع متطورة جدا.
2>&1
هو POSIX قذيفة بناء.هنا هو انهيار رمز من رمز:
2
: "الخطأ القياسي"إخراج ملف واصف.
>&
: مكررة ملف إخراج واصف مشغل (البديل إعادة توجيه الإخراج المشغل >
).نظرا [x]>&[y]
, الملف واصف تدل x
إلى أن نسخ الملف الناتج واصف y
.
1
"الإخراج القياسي"إخراج ملف واصف.
التعبير 2>&1
نسخ ملف واصف 1
الموقع 2
, لذا أي إخراج كتب 2
("معيار الخطأ") في بيئة التنفيذ يذهب إلى نفس الملف في الأصل وصفها 1
("الإخراج القياسية").
مزيد من التوضيح:
ملف واصف:"لكل عملية فريدة من نوعها, غير سلبية صحيح المستخدمة لتحديد ملف مفتوح لغرض الوصول إلى الملفات."
معيار الإخراج/خطأ:الرجوع إلى الملاحظة التالية في إعادة توجيه القسم قذيفة الوثائق:
فتح الملفات يتم تمثيل الأرقام العشرية بدءا من الصفر.أكبر قيمة ممكنة هو تنفيذ محددة;ومع ذلك ، فإن جميع التطبيقات يجب دعم على الأقل 0 إلى 9 ، شاملة ، للاستخدام من قبل التطبيق.هذه الأرقام تسمى "واصفات الملف".القيم 0 و 1 و 2 يكون معنى خاص التقليدية يستخدم وضمنا من قبل بعض توجيه العمليات ؛ ويشار إليها باسم الإدخال القياسية القياسية الناتج الخطأ القياسي ، على التوالي.البرامج عادة ما تأخذ مدخلات من المدخلات القياسية ، واكتب الناتج على الإخراج القياسي.رسائل الخطأ عادة ما تكون مكتوبة على الخطأ القياسي.إعادة توجيه يمكن للمشغلين أن يسبقه واحد أو أكثر من أرقام (بدون تدخل الأحرف المسموح بها) للدلالة على ملف واصف عدد.
و2 هو الخطأ المعياري وحدة التحكم.
1 هو الإخراج القياسي حدة التحكم.
وهذا هو يونكس القياسية، ويندوز أيضا يتبع POSIX.
ومنها مثلا. عند تشغيل
perl test.pl 2>&1
ويتم توجيه الخطأ القياسي إلى الإخراج القياسي، حتى تتمكن من رؤية كل من نواتج معا:
perl test.pl > debug.log 2>&1
وبعد التنفيذ، ويمكنك ان ترى كل الإخراج، بما في ذلك أخطاء في debug.log.
perl test.pl 1>out.log 2>err.log
وبعد ذلك يذهب إلى الإخراج القياسي out.log، والخطأ المعياري لerr.log.
وأقترح عليك في محاولة لفهم هذه.
للإجابة على سؤالك:فإنه يأخذ أي خطأ الإخراج (عادة إرسالها إلى stderr) ويكتب إلى الإخراج القياسي (المعياري).
هذا هو مفيدة ، على سبيل المثال 'أكثر' عندما كنت في حاجة ترحيل جميع الإخراج.بعض البرامج مثل استخدام الطباعة المعلومات في stderr.
لمساعدتك على تذكر
- 1 = الإخراج القياسي (حيث برامج طباعة الإخراج الطبيعي)
- 2 = الخطأ القياسي (حيث البرامج أخطاء الطباعة)
"2>&1" يشير ببساطة كل شيء إرسالها إلى stderr ، المعياري بدلا من ذلك.
وأوصى أيضا القراءة هذا المنصب على خطأ إعادة توجيه حيث تم تناول هذا الموضوع بالتفصيل الكامل.
من وجهة مبرمج وجهة نظر، فهذا يعني بالضبط هذا:
dup2(1, 2);
وفهم أن 2>&1
هو نسخة م> يفسر أيضا لماذا ...
command >file 2>&1
... ليست هي نفسها كما ...
command 2>&1 >file
وأول سترسل كل من تيارات لfile
، في حين أن الثانية سترسل الأخطاء stdout
، والإخراج العادي في file
.
الناس, تذكر دائما paxdiablo's تلميح عن الحالي موقع توجيه الهدف...ذلك هو المهم.
رأيي الشخصي ذاكري من أجل 2>&1
المشغل هو هذا:
- التفكير
&
بمعنى'and'
أو'add'
(الحرف هو ampers-و, أليس كذلك؟) - بحيث يصبح: 'إعادة توجيه
2
(stderr) إلى أين1
(المعياري) بالفعل/حاليا ، إضافة كل تيارات'.
نفس ذاكري يعمل الأخرى المستخدمة بشكل متكرر إعادة التوجيه أيضا ، 1>&2
:
- التفكير
&
معنىand
أوadd
...(يمكنك الحصول على فكرة عن العطف؟) - بحيث يصبح: 'إعادة توجيه
1
(المعياري) إلى أين2
(stderr) بالفعل/حاليا ، إضافة كل تيارات'.
وتذكر دائما:عليك أن تقرأ سلاسل من إعادة توجيه من نهاية' ، من اليمين إلى اليسار (لا من اليسار إلى اليمين).
شريطة أن /foo
غير موجود على النظام الخاص بك /tmp
لا...
$ ls -l /tmp /foo
سيتم طباعة محتويات /tmp
و طباعة رسالة خطأ على /foo
$ ls -l /tmp /foo > /dev/null
سوف ترسل محتويات /tmp
إلى /dev/null
و طباعة رسالة خطأ على /foo
$ ls -l /tmp /foo 1> /dev/null
سوف تفعل بالضبط نفس (لاحظ 1)
$ ls -l /tmp /foo 2> /dev/null
سيتم طباعة محتويات /tmp
وإرسال رسالة الخطأ /dev/null
$ ls -l /tmp /foo 1> /dev/null 2> /dev/null
سيتم إرسال كل من القائمة فضلا عن رسالة الخطأ /dev/null
$ ls -l /tmp /foo > /dev/null 2> &1
هو الاختزال
وهذا هو تماما مثل تمرير الخطأ إلى المعياري أو المحطة.
وهذا هو، cmd
ليس الأمر:
$cmd 2>filename
cat filename
command not found
ويتم إرسال الخطأ إلى ملف مثل هذا:
2>&1
ويتم إرسالها الخطأ المعياري للمحطة.
إعادة توجيه المدخلات
توجيه المدخلات أسباب ملف اسمه النتائج من التوسع كلمة فتح للقراءة على الملف واصف ن ، أو الإدخال القياسي (ملف واصف 0) إذا كان n غير محدد.
شكل إعادة توجيه الإدخال:
[n]<word
إعادة توجيه الإخراج
توجيه الإخراج أسباب الملف الذي اسم النتائج من التوسع في الكلمة إلى أن فتح باب الكتابة على ملف واصف ن ، أو الإخراج القياسي (ملف واصف 1) إذا كان n لم يتم تحديد.إذا كان الملف غير موجود إنشائه ؛ إذا كان موجود يتم اقتطاعه من الصفر الحجم.
شكل إعادة توجيه الإخراج:
[n]>word
تحريك ملف واصف
إعادة توجيه المشغل ،
[n]<&digit-
ينتقل الملف واصف رقم ملف واصف ن ، أو الإدخال القياسي (ملف واصف 0) إذا كان n هو غير محدد.أرقام أغلقت بعد أن تكرار n.
وبالمثل ، فإن إعادة توجيه المشغل
[n]>&digit-
ينتقل الملف واصف رقم ملف واصف ن ، أو الإخراج القياسي (ملف واصف 1) إذا كان n هو غير محدد.
Ref:
man bash
نوع /^REDIRECT
لتحديد موقع إلى redirection
القسم ومعرفة المزيد...
النسخة الإلكترونية هنا: 3.6 إعادة توجيه
PS:
الكثير من الوقت ، man
هو أداة قوية لتعلم لينكس.
0 المدخلات ، 1 ل المعياري و 2 stderr.
طرف واحد:
somecmd >1.txt 2>&1
هو الصحيح ، في حين somecmd 2>&1 >1.txt
تماما الخطأ مع أي تأثير!