МощнаяОболочка
Jan. 14th, 2019 04:33 pmНа прошедших рожденственских каникулах наконец дошли руки посидеть с PowerShell. Тем более что последняя версия мигрировала на .NET Core и полностью кроссплатформенная. Все последующие версии тоже будут только на .NET Core.
У меня мало опыта с .NET, трогал пару раз в прошлом, но несерьёзно, поэтому было интересно что и как там сейчас. Я долго не брался за PowerShell хотя видел как многие пользуются им и фанатеют. Думал, ну может это как VIM: или ненависть или любовь до гроба, посередине почти не бывает. Для меня лично причины игнорировать PowerShell были такие (забегая вперёд, все эти опасения не оправдались):
Итоги:
Ни одно из вышеперечисленных опасений не оправдалось:
То, что удивило или не понравилось:
У меня мало опыта с .NET, трогал пару раз в прошлом, но несерьёзно, поэтому было интересно что и как там сейчас. Я долго не брался за PowerShell хотя видел как многие пользуются им и фанатеют. Думал, ну может это как VIM: или ненависть или любовь до гроба, посередине почти не бывает. Для меня лично причины игнорировать PowerShell были такие (забегая вперёд, все эти опасения не оправдались):
- Странный и слишком избыточный синтаксис, который отпугивает. Кажется что нормальный человек все эти
Get-ChildItemиNew-ItemProperty(да ещё и с миллионом параметров каждый) никогда не выучит. И руки обломаются писать такую колбасу на каждую ерунду в шелле. - Необходимость серьёзно разбираться с .NET если хочется нормальной производительности.
- Лень и сила привычки. Тем более что под Виндой я легко себе могу сделать Linux-подобную среду, а вот наоборот - нет. Поэтому лучше уж сразу инвестировать в bash и GNU toolchain и пользоваться ими везде, чем под каждую платформу учить уникальные вещи.
Итоги:
Ни одно из вышеперечисленных опасений не оправдалось:
- Несмотря на длинные имена команд, в PowerShell предопределены алиасы на всё что используется чаще всего. Поэтому особо много писать не требуется. В 98% случаев я не пользовался полными именами, хватало алиасов.
- Множество параметров тоже не пришлось зубрить, т.к. шелл поддерживает Tab-completion. Причём, он довольно умный и сначала предлагает наиболее релевантные параметры.
- За все 25 задач в Advent Of Code в собственно .NET пришлось залезть лишь пару раз: 1) хотел сделать настоящий двумерный массив, а не jagged array; 2) надо было использовать regexp чуть менее тривиальный.
То, что удивило или не понравилось:
- Неожиданностью было то, что округление целых не как в С/С++, а Round half to even. Т.е., число округляется до ближайшего чётного целого. Например, 1.5 и 2.5 будут округлены как 2.
- Непоследовательный синтакс для вызовов встроенных шелловских функций и .NET методов. Например:
PowerShell function call:Foo -param1 "a" -param2 "b"
или с неявными параметрами:Foo "a" "b"
Но при этом:$a = [math]::Truncate(7/2)
Иногда есть скобки, иногда нет. - Недоделанная работа с unsigned integers. Такой код приводит к ошибке:
[uint32]$a = 0xffffffff. Обходится это таким уродством:[uint32]$a = "0xffffffff". Надеюсь в будущем исправят.
- Новый подход к шеллу: всё объект. Для программиста это родная среда, не надо заниматься утомительным расковыриванием текста как часто приходится делать в bash. Например, чтобы показать в рабочей директории все файлы размером больше 10К, отсорторованными по дате создания:
gci | where Length -gt 10kb | sort CreationTime
gciэто алиасGet-ChildItem. При этом та же командаGet-ChildItemбудет работать на любой древовидной структуре, файловая система или ещё что. - Приятный синтаксический сахар. Например,
switchна стероидах:switch -file $somePath { 1 { echo "1" } "two" { echo "2" } { $_ -like "wtf"} { echo "hm.." } { $_ -in "a",$b,42 } { echo "got $_" } default { throw "error: $_" } }Каждая строка в файле будет обработана в этом switch'е.
Типа, лямбда:$foo = { param($x) $x * 2 } &$foo 2 4Можно передавать$fooв другие функции и пр. - Нет 40-летней legacy как в bash. Всё унифицировано, все команды и параметры работают везде одинаково. Поэтому учить приходится довольно мало при кажущемся богатстве синтаксиса и объектов.