Есть ли какой-нибудь магический конструктор, к которому я не обращаюсь?
Нет, в компиляторе есть волшебный соус c - всякий раз, когда компилятор PowerShell видит выражение приведения, где правая Сторона - это словарь, а у литерала типа есть точное имя pscustomobject
, он будет рассматривать словарь или хеш-таблицу (литерал или нет) как упорядоченный словарь и преобразовывать его в PSObject
.
Начиная с VisitConvertExpression
в Compiler.cs :
var typeName = convertExpressionAst.Type.TypeName;
var hashTableAst = convertExpressionAst.Child as HashtableAst;
Expression childExpr = null;
if (hashTableAst != null)
{
var temp = NewTemp(typeof(OrderedDictionary), "orderedDictionary");
if (typeName.FullName.Equals(LanguagePrimitives.OrderedAttribute, StringComparison.OrdinalIgnoreCase))
{
return Expression.Block(
typeof(OrderedDictionary),
new[] { temp },
BuildHashtable(hashTableAst.KeyValuePairs, temp, ordered: true));
}
if (typeName.FullName.Equals("PSCustomObject", StringComparison.OrdinalIgnoreCase))
{
// pure laziness here - we should construct the PSObject directly. Instead, we're relying on the conversion
// to create the PSObject from an OrderedDictionary.
childExpr = Expression.Block(
typeof(OrderedDictionary),
new[] { temp },
BuildHashtable(hashTableAst.KeyValuePairs, temp, ordered: true));
}
}
Обратите внимание, как это также приводит к тому, что [ordered]@{Key='Value'}
приводит к OrderedDictionary