كيفية الحصول على حدد الكائن في العودة الخام نوع (مثلا ، سلسلة) بدلا من PSCustomObject?

StackOverflow https://stackoverflow.com/questions/618749

  •  03-07-2019
  •  | 
  •  

سؤال

التعليمة البرمجية التالية يعطيني مجموعة من PSCustomObjects, كيف يمكنني الحصول عليه العودة مجموعة من السلاسل ؟

$files = Get-ChildItem $directory -Recurse | Select-Object FullName | Where-Object {!($_.psiscontainer)}

(الثانوي السؤال ما psiscontainer جزء ؟ لقد نسخت هذا من مثال على الإنترنت)

بعد قبول تحرير: اثنين إجابات كبيرة, أتمنى أن علامة كل منهم.وقد منحت الأصلي الإجابة.

هل كانت مفيدة؟

المحلول

تحتاج فقط إلى اختيار العقار تريد من الكائنات. FullName في هذه الحالة.

$files = Get-ChildItem $directory -Recurse | Select-Object FullName | Where-Object {!($_.psiscontainer)} | foreach {$_.FullName}

تحرير: تفسير مرقس الذي يسأل: "ماذا foreach تفعل ؟ ما هو تعداد؟"

سونغ مايستر شرح جيد جدا ، ولكن سأضيف تجول هنا لأنه يمكن أن تكون مفيدة.

المفهوم الأساسي هو خط أنابيب.صورة سلسلة من بينغبونغ الكرات المتداول أسفل أنبوب ضيق واحدة بعد الأخرى.هذه الكائنات في خط أنابيب.كل مرحلة من خط أنابيب--رمز قطاعات مفصولة الأنابيب (|) حرفا-قد الأنابيب الخوض في ذلك الأنابيب الخروج منه.الناتج من مرحلة واحدة متصلة مدخلات المرحلة المقبلة.كل مرحلة تستغرق الكائنات وصولهم ، لا شيء لهم ويرسل لهم بالعودة إلى إخراج أنابيب أو يرسل جديدة واستبدال الكائنات.

Get-ChildItem $directory -Recurse

الحصول على ChildItem يمشي من خلال الملفات خلق FileSystemInfo الكائنات التي تمثل كل ملف و الدليل أنه واجه و يضعهم في خط أنابيب.

Select-Object FullName

حدد الكائن يأخذ كل FileSystemInfo كائن وصولها يمسك الخاصية FullName من ذلك (وهو مسار في هذه الحالة) ، يضع ذلك في العلامة التجارية الجديدة كائن مخصص أنها خلقت ، ويضع أن العرف الكائن في خط أنابيب.

Where-Object {!($_.psiscontainer)}

هذا هو مرشح.فإنه يأخذ كل كائن ، يدرس ، ويرسله مرة أخرى أو يتجاهل ذلك اعتمادا على بعض الشروط.الكود الخاص بك هنا خلل بالمناسبة.مخصص الكائنات التي تصل إلى هنا لم يكن لديك psiscontainer الملكية.هذه المرحلة لا تفعل في الواقع أي شيء.سونغ مايستر رمز هو أفضل.

foreach {$_.FullName}

Foreach الذين طويلة اسم ForEach-كائن الاستيلاء على كل كائن وصولها ، وهنا يمسك الخاصية FullName, سلسلة, من ذلك.الآن هنا هو خفية الجزء:أي القيمة التي لا تستهلك هذا ليس التقاطها بواسطة متغير أو قمعها في بعض الطريق ، ووضعها في انتاج الانابيب.كتجربة ، حاول استبدال تلك المرحلة مع هذا:

foreach {'hello'; $_.FullName; 1; 2; 3}

في الواقع محاولة دراسة الإخراج.هناك أربع قيم في كتلة التعليمات البرمجية.لا أحد منهم المستهلكة.لاحظت أنها تظهر في الإخراج.الآن جرب هذا:

foreach {'hello'; $_.FullName; $ x = 1; 2; 3}

لاحظت أن واحدة من القيم التي تم التقاطها عن طريق متغير.لا تظهر في انتاج الانابيب.

نصائح أخرى

للحصول على سلسلة اسم الملف يمكنك استخدام

$files = Get-ChildItem $directory -Recurse | Where-Object {!($_.psiscontainer)} | Select-Object -ExpandProperty FullName

على -ExpandProperty المعلمة يسمح لك للحصول على العودة كائن على أساس نوع العقار المحدد.

مزيد من التجارب تبين أن هذا لم ينجح مع V1, ولكن هذه الوظيفة هو ثابت من V2 CTP3.

عن السؤال #1

يجب إزالة "حدد الكائن" جزء - انها زائدة عن الحاجة و نقل "حيث" مرشح قبل "foreach" على عكس dangph الجواب - تصفية أقرب وقت ممكن حتى أن كنت تتعامل مع مجموعة فرعية فقط من ما لديك للتعامل مع القادم خط الأنابيب.

$files = Get-ChildItem $directory -Recurse | Where-Object {!$_.PsIsContainer} | foreach {$_.FullName}

هذا مقتطف الشفرة أساسا يقرأ

  • الحصول على جميع الملفات المسار الكامل من كافة الملفات بشكل متكرر (على-ChildItem $الدليل Recurse)
  • تصفية الدلائل (حيث-Object {!$_.PsIsContainer})
  • عودة كامل اسم الملف فقط (foreach {$_.FullName})
  • حفظ جميع أسماء الملفات في الملفات

علما بأن foreach {$_.FullName}, في powershell البيان الأخير في كتلة البرنامج النصي ({...}) هو عاد ، في هذه الحالة $_.FullName من نوع string

إذا كنت حقا بحاجة للحصول على الخام كائن, أنت لا تحتاج إلى القيام بأي شيء بعد التخلص من "حدد الكائن".إذا كنت تريد استخدام حدد الكائن ولكن ترغب في الحصول الخام كائن استخدام "PsBase" ، الذي هو مختلف تماما عن السؤال(الموضوع) - راجع "ما الأمر مع PSBASE, PSEXTENDED, PSADAPTED ، PSOBJECT?"للحصول على مزيد من المعلومات حول هذا الموضوع

السؤال رقم 2

وأيضا تصفية من قبل !$_.PsIsContainer يعني أنك باستثناء حاوية مستوى الأجسام - في حالتك أنت تفعل الحصول على ChildItem على الملفات مزود(يمكنك أن ترى PowerShell مقدمي الخدمات من خلال الحصول على PsProvider) ، لذلك الحاوية هو DirectoryInfo(مجلد)

PsIsContainer يعني أشياء مختلفة تحت مختلف PowerShell مقدمي;على سبيل المثال) من أجل التسجيل مزود PsIsContainer هو من نوع مايكروسوفت.Win32.RegistryKey جرب هذا:

>pushd HKLM:\SOFTWARE
>ls | gm

[تحديث] إلى السؤال التالي: ماذا foreach تفعل ؟ ما هو تعداد ؟ إلى توضيح ، "foreach" هو اسم مستعار "Foreach-كائن" يمكنك معرفة ذلك من خلال ،

get-help foreach

- أو -

get-alias foreach

الآن في جوابي "foreach" هو تعداد كل مثيل كائن من نوع FileInfo عاد من السابق الأنابيب (التي تمت تصفيتها الدلائل). FileInfo لديه خاصية تسمى FullName وهذا ما "foreach" هو تعداد أكثر.
و لك مرجع الكائن الذي تم تمريره من خلال خط أنابيب من خلال خط أنابيب متغير يسمى "$_" وهو من نوع FileInfo داخل كتلة البرنامج النصي سياق "foreach".

V1, إضافة عامل التصفية التالية إلى ملف التعريف الخاص بك:

filter Get-PropertyValue([string]$name) { $_.$name }

ثم يمكنك أن تفعل هذا:

gci . -r | ?{!$_.psiscontainer} | Get-PropertyName fullname

راجع للشغل, إذا كنت تستخدم PowerShell المجتمع امتداد لديك بالفعل هذا.

بشأن القدرة على استخدام Select Object-التوسع في V2 هو خدعة لطيف لكن ليس واضحا حقا ليس ما حدد الكائن أو توسيع المقصود.-توسيع كل شيء عن تسطيح مثل ينق SelectMany واختر الكائن عن إسقاط خصائص متعددة على كائن مخصص.

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top