Compartir a través de


about_Classes_Properties

Descripción breve

Describe cómo definir propiedades para las clases de PowerShell.

Descripción larga

Las propiedades son miembros de la clase que contienen datos. Las propiedades se declaran como variables en el ámbito de clase. Una propiedad puede ser de cualquier tipo integrado o de una instancia de otra clase. Las clases pueden tener cero o más propiedades. Las clases no tienen un recuento máximo de propiedades.

Las propiedades de clase pueden tener cualquier número de atributos, incluidos los atributos ocultos y estáticos . Cada definición de propiedad debe incluir un tipo para la propiedad . Puede definir un valor predeterminado para una propiedad.

Sintaxis

Las propiedades de clase usan las sintaxis siguientes:

Sintaxis de una línea

[[<attribute>]...] [<property-type>] $<property-name> [= <default-value>]

Sintaxis multilínea

[[<attribute>]...]
[<property-type>]
$<property-name> [= <default-value>]

Ejemplos

Ejemplo 1: Propiedades de clase mínimas

Las propiedades de la clase ExampleProject1 usan tipos integrados sin atributos ni valores predeterminados.

class ExampleProject1 {
    [string]   $Name
    [int]      $Size
    [bool]     $Completed
    [string]   $Assignee
    [datetime] $StartDate
    [datetime] $EndDate
    [datetime] $DueDate
}

[ExampleProject1]::new()

$null -eq ([ExampleProject1]::new()).Name
Name      :
Size      : 0
Completed : False
StartDate : 1/1/0001 12:00:00 AM
EndDate   : 1/1/0001 12:00:00 AM
DueDate   : 1/1/0001 12:00:00 AM

True

El valor predeterminado de las propiedades Name y Assignee es $null porque se escriben como cadenas, que es un tipo de referencia. Las otras propiedades tienen el valor predeterminado para su tipo definido, ya que son propiedades de tipo de valor. Para obtener más información sobre los valores predeterminados de las propiedades, vea Valores de propiedad predeterminados.

Ejemplo 2: Propiedades de clase con tipos personalizados

Las propiedades de ExampleProject2 incluyen una enumeración personalizada y una clase definidas en PowerShell antes de la clase ExampleProject2 .

enum ProjectState {
    NotTriaged
    ReadyForWork
    Committed
    Blocked
    InProgress
    Done
}

class ProjectAssignee {
    [string] $DisplayName
    [string] $UserName

    [string] ToString() {
        return "$($this.DisplayName) ($($this.UserName))"
    }
}

class ExampleProject2 {
    [string]          $Name
    [int]             $Size
    [ProjectState]    $State
    [ProjectAssignee] $Assignee
    [datetime]        $StartDate
    [datetime]        $EndDate
    [datetime]        $DueDate
}

[ExampleProject2]@{
    Name     = 'Class Property Documentation'
    Size     = 8
    State    = 'InProgress'
    Assignee = @{
        DisplayName = 'Mikey Lombardi'
        UserName    = 'michaeltlombardi'
    }
    StartDate = '2023-10-23'
    DueDate   = '2023-10-27'
}
Name      : Class Property Documentation
Size      : 8
State     : InProgress
Assignee  : Mikey Lombardi (michaeltlombardi)
StartDate : 10/23/2023 12:00:00 AM
EndDate   : 1/1/0001 12:00:00 AM
DueDate   : 10/27/2023 12:00:00 AM

Ejemplo 3: propiedad class con un atributo de validación

La clase ExampleProject3 define la propiedad Size como un entero que debe ser mayor o igual que 0 y menor o igual que 16. Usa el atributo ValidateRange para limitar el valor.

class ExampleProject3 {
                           [string]   $Name
    [ValidateRange(0, 16)] [int]      $Size
                           [bool]     $Completed
                           [string]   $Assignee
                           [datetime] $StartDate
                           [datetime] $EndDate
                           [datetime] $DueDate
}

$project = [ExampleProject3]::new()
$project
Name      :
Size      : 0
Completed : False
Assignee  :
StartDate : 1/1/0001 12:00:00 AM
EndDate   : 1/1/0001 12:00:00 AM
DueDate   : 1/1/0001 12:00:00 AM

Cuando ExampleProject3 crea instancias, el valor predeterminado De tamaño es 0. Al establecer la propiedad en un valor dentro del intervalo válido, se actualiza el valor.

$project.Size = 8
$project
Name      :
Size      : 8
Completed : False
Assignee  :
StartDate : 1/1/0001 12:00:00 AM
EndDate   : 1/1/0001 12:00:00 AM
DueDate   : 1/1/0001 12:00:00 AM

Cuando Size se establece en un valor no válido fuera del intervalo, PowerShell genera una excepción y el valor no cambia.

$project.Size = 32
$project.Size = -1

$project
Exception setting "Size": "The 32 argument is greater than the maximum
allowed range of 16. Supply an argument that is less than or equal to 16
and then try the command again."
At line:1 char:1
+ $project.Size = 32
+ ~~~~~~~~~~~~~~~~~~
    + CategoryInfo          : NotSpecified: (:) [], SetValueInvocationExc
   eption
    + FullyQualifiedErrorId : ExceptionWhenSetting

Exception setting "Size": "The -1 argument is less than the minimum
allowed range of 0. Supply an argument that is greater than or equal to 0
and then try the command again."
At line:1 char:1
+ $project.Size = -1
+ ~~~~~~~~~~~~~~~~~~
    + CategoryInfo          : NotSpecified: (:) [], SetValueInvocationExc
   eption
    + FullyQualifiedErrorId : ExceptionWhenSetting

Name      :
Size      : 8
Completed : False
Assignee  :
StartDate : 1/1/0001 12:00:00 AM
EndDate   : 1/1/0001 12:00:00 AM
DueDate   : 1/1/0001 12:00:00 AM

Ejemplo 4: propiedad class con un valor predeterminado explícito

La clase ExampleProject4 establece de forma predeterminada el valor de la propiedad StartDate en la fecha actual.

class ExampleProject4 {
    [string]   $Name
    [int]      $Size
    [bool]     $Completed
    [string]   $Assignee
    [datetime] $StartDate = (Get-Date).Date
    [datetime] $EndDate
    [datetime] $DueDate
}

[ExampleProject4]::new()

[ExampleProject4]::new().StartDate -eq (Get-Date).Date
Name      :
Size      : 0
Completed : False
Assignee  :
StartDate : 10/23/2023 12:00:00 AM
EndDate   : 1/1/0001 12:00:00 AM
DueDate   : 1/1/0001 12:00:00 AM

True

Ejemplo 5: propiedad de clase oculta

La propiedad Guid de la clase ExampleProject5 tiene la hidden palabra clave . La propiedad Guid no se muestra en la salida predeterminada de la clase o en la lista de propiedades devueltas por Get-Member.

class ExampleProject5 {
           [string]   $Name
           [int]      $Size
           [bool]     $Completed
           [string]   $Assignee
           [datetime] $StartDate
           [datetime] $EndDate
           [datetime] $DueDate
    hidden [string]   $Guid      = (New-Guid).Guid
}

$project = [ExampleProject5]::new()

"Project GUID: $($project.Guid)"

$project

$project | Get-Member -MemberType Properties | Format-Table
Project GUID: c72cef84-057c-4649-8940-13490dcf72f0

Name      :
Size      : 0
Completed : False
Assignee  :
StartDate : 1/1/0001 12:00:00 AM
EndDate   : 1/1/0001 12:00:00 AM
DueDate   : 1/1/0001 12:00:00 AM


   TypeName: ExampleProject5

Name      MemberType Definition
----      ---------- ----------
Assignee  Property   string Assignee {get;set;}
Completed Property   bool Completed {get;set;}
DueDate   Property   datetime DueDate {get;set;}
EndDate   Property   datetime EndDate {get;set;}
Name      Property   string Name {get;set;}
Size      Property   int Size {get;set;}
StartDate Property   datetime StartDate {get;set;}

Ejemplo 6: propiedad de clase estática

La clase ExampleProject6 define la propiedad Static Projects como una lista de todos los proyectos creados. El constructor predeterminado de la clase agrega la nueva instancia a la lista de proyectos.

class ExampleProject6 {
           [string]            $Name
           [int]               $Size
           [bool]              $Completed
           [string]            $Assignee
           [datetime]          $StartDate
           [datetime]          $EndDate
           [datetime]          $DueDate
    hidden [string]            $Guid     = (New-Guid).Guid
    static [ExampleProject6[]] $Projects = @()

    ExampleProject6() {
        [ExampleProject6]::Projects += $this
    }
}

"Project Count: $([ExampleProject6]::Projects.Count)"

$project1 = [ExampleProject6]@{ Name = 'Project_1' }
$project2 = [ExampleProject6]@{ Name = 'Project_2' }

[ExampleProject6]::Projects | Select-Object -Property Name, Guid
Project Count: 0

Name      Guid
----      ----
Project_1 75e7c8a0-f8d1-433a-a5be-fd7249494694
Project_2 6c501be4-e68c-4df5-8fce-e49dd8366afe

Ejemplo 7: Definición de una propiedad en el constructor

La clase ExampleProject7 define la propiedad Duration script en el constructor de clase estática con el Update-TypeData cmdlet . El uso del Update-TypeData cmdlet o Add-Member es la única manera de definir propiedades avanzadas para las clases de PowerShell.

La propiedad Duration devuelve un valor de $null a menos que se establezcan las propiedades StartDate y EndDate y StartDate para que sean anteriores a EndDate.

class ExampleProject7 {
    [string]   $Name
    [int]      $Size
    [bool]     $Completed
    [string]   $Assignee
    [datetime] $StartDate
    [datetime] $EndDate
    [datetime] $DueDate

    static [hashtable[]] $MemberDefinitions = @(
        @{
            MemberName = 'Duration'
            MemberType = 'ScriptProperty'
            Value      = {
                [datetime]$UnsetDate = 0

                $StartNotSet   = $this.StartDate -eq $UnsetDate
                $EndNotSet     = $this.EndDate   -eq $UnsetDate
                $StartAfterEnd = $this.StartDate -gt $this.EndDate

                if ($StartNotSet -or $EndNotSet -or $StartAfterEnd) {
                    return $null
                }

                return $this.EndDate - $this.StartDate
            }
        }
    )

    static ExampleProject7() {
        $TypeName = [ExampleProject7].Name
        foreach ($Definition in [ExampleProject7]::MemberDefinitions) {
            Update-TypeData -TypeName $TypeName @Definition
        }
    }

    ExampleProject7() {}

    ExampleProject7([string]$Name) {
        $this.Name = $Name
    }
}

$Project = [ExampleProject7]::new()
$Project

$null -eq $Project.Duration
Duration  :
Name      :
Size      : 0
Completed : False
Assignee  :
StartDate : 1/1/0001 12:00:00 AM
EndDate   : 1/1/0001 12:00:00 AM
DueDate   : 1/1/0001 12:00:00 AM

True

La vista predeterminada de una instancia de la clase ExampleProject7 incluye la duración. Dado que no se establecen las propiedades StartDate y EndDate , la propiedad Duration es $null.

$Project.StartDate = '2023-01-01'
$Project.EndDate   = '2023-01-08'

$Project
Duration  : 7.00:00:00
Name      :
Size      : 0
Completed : False
Assignee  :
StartDate : 1/1/2023 12:00:00 AM
EndDate   : 1/8/2023 12:00:00 AM
DueDate   : 1/1/0001 12:00:00 AM

Con las propiedades establecidas correctamente, la propiedad Duration devuelve un intervalo de tiempo que representa cuánto tiempo se ejecutó el proyecto.

Valores de propiedad predeterminados

Cada propiedad de clase tiene un valor predeterminado implícito en función del tipo de la propiedad.

Si una propiedad es un tipo de referencia, como una cadena o un objeto, el valor predeterminado implícito es $null. Si una propiedad es un tipo de valor, como un número, un valor booleano o una enumeración, la propiedad tiene un valor predeterminado en función del tipo:

  • Tipos numéricos, como enteros y números de punto flotante, de forma predeterminada 0
  • Valores booleanos predeterminados $false
  • Las enumeraciones tienen como valor predeterminado 0, incluso la enumeración no define una etiqueta para 0.

Para obtener más información sobre los valores predeterminados en .NET, vea Valores predeterminados de tipos de C# (referencia de C#).

Para definir un valor predeterminado explícito para una propiedad, declare la propiedad con una asignación al valor predeterminado.

Por ejemplo, esta definición para la clase ProjectTask define un valor predeterminado explícito para la propiedad Guid , asignando un GUID aleatorio a cada nueva instancia.

class ProjectTask {
    [string] $Name
    [string] $Description
    [string] $Guid = (New-Guid).Guid
}

[ProjectTask]::new()
Name Description Guid
---- ----------- ----
                 aa96350c-358d-465c-96d1-a49949219eec

Las propiedades ocultas y estáticas también pueden tener valores predeterminados.

Propiedades ocultas

Puede ocultar las propiedades de una clase declarandolas con la hidden palabra clave . Las propiedades de clase ocultas son:

  • No se incluye en la salida predeterminada de la clase .
  • No se incluye en la lista de miembros de clase devueltos por el Get-Member cmdlet . Para mostrar las propiedades ocultas con Get-Member, use el parámetro Force .
  • No se muestra en la finalización de tabulación o En IntelliSense, a menos que se produzca la finalización en la clase que define la propiedad oculta.
  • Miembros públicos de la clase . Se puede acceder a ellos y modificarlos. Ocultar una propiedad no lo hace privado. Solo oculta la propiedad como se describe en los puntos anteriores.

Para obtener más información sobre la hidden palabra clave , consulte about_Hidden.

Propiedades estáticas

Puede definir una propiedad como perteneciente a la propia clase en lugar de las instancias de la clase declarando la propiedad con la static palabra clave . Propiedades de clase estáticas:

  • Siempre están disponibles, independientemente de la creación de instancias de clase.
  • Se comparten en todas las instancias de la clase .
  • Siempre están disponibles.
  • Son modificables. Se pueden actualizar las propiedades estáticas. No son inmutables de forma predeterminada.
  • Live para todo el intervalo de sesión.

Importante

Las propiedades estáticas de las clases definidas en PowerShell no son inmutables. Pueden

Propiedades de clase derivadas

Cuando una clase deriva de una clase base, hereda las propiedades de la clase base. Las propiedades definidas en la clase base, incluidas las propiedades ocultas, están disponibles en la clase derivada.

Una clase derivada puede invalidar una propiedad heredada redefinindola en la definición de clase. La propiedad de la clase derivada usa el tipo redefinido y el valor predeterminado, si existe. Si la propiedad heredada definió un valor predeterminado y la propiedad redefinida no, la propiedad heredada no tiene ningún valor predeterminado.

Si una clase derivada no invalida una propiedad estática, el acceso a la propiedad estática a través de la clase derivada tiene acceso a la propiedad estática de la clase base. Al modificar el valor de propiedad a través de la clase derivada, se modifica el valor de la clase base. Cualquier otra clase derivada que no invalide la propiedad estática también usa el valor de la propiedad en la clase base. Actualizar el valor de una propiedad estática heredada en una clase que no invalida la propiedad podría tener efectos no deseados para las clases derivadas de la misma clase base.

En el ejemplo siguiente se muestra el comportamiento de las propiedades estáticas y de instancia en las clases derivadas.

class BaseClass {
    static [string] $StaticProperty = 'Static'
    [string] $InstanceProperty = 'Instance'
}
class DerivedClassA : BaseClass     {}
class DerivedClassB : BaseClass     {}
class DerivedClassC : DerivedClassB {
    [string] $InstanceProperty
}
class DerivedClassD : BaseClass {
    static [string] $StaticProperty = 'Override'
    [string] $InstanceProperty = 'Override'
}

"Base instance      => $([BaseClass]::new().InstanceProperty)"
"Derived instance A => $([DerivedClassA]::new().InstanceProperty)"
"Derived instance B => $([DerivedClassB]::new().InstanceProperty)"
"Derived instance C => $([DerivedClassC]::new().InstanceProperty)"
"Derived instance D => $([DerivedClassD]::new().InstanceProperty)"
Base instance      => Instance
Derived instance A => Instance
Derived instance B => Instance
Derived instance C =>
Derived instance D => Override

InstanceProperty para DerivedClassC es una cadena vacía porque la clase redefinió la propiedad sin establecer un valor predeterminado. Para DerivedClassD , el valor es Override porque la clase redefinió la propiedad con esa cadena como valor predeterminado.

"Base static        => $([BaseClass]::StaticProperty)"
"Derived static A   => $([DerivedClassA]::StaticProperty)"
"Derived static B   => $([DerivedClassB]::StaticProperty)"
"Derived static C   => $([DerivedClassC]::StaticProperty)"
"Derived static D   => $([DerivedClassD]::StaticProperty)"
Base static        => Static
Derived static A   => Static
Derived static B   => Static
Derived static C   => Static
Derived static D   => Override

A excepción de DerivedClassD, el valor de la propiedad estática para las clases derivadas es el mismo que la clase base, ya que no vuelven a definir la propiedad. Esto se aplica incluso a DerivedClassC, que hereda de DerivedClassB en lugar de directamente de BaseClass.

[DerivedClassA]::StaticProperty = 'Updated from A'
"Base static        => $([BaseClass]::StaticProperty)"
"Derived static A   => $([DerivedClassA]::StaticProperty)"
"Derived static B   => $([DerivedClassB]::StaticProperty)"
"Derived static C   => $([DerivedClassC]::StaticProperty)"
"Derived static D   => $([DerivedClassD]::StaticProperty)"
Base static        => Updated from A
Derived static A   => Updated from A
Derived static B   => Updated from A
Derived static C   => Updated from A
Derived static D   => Override

Cuando se accede a StaticProperty y se modifica a través de DerivedClassA, el valor cambiado afecta a todas las clases excepto a DerivedClassD.

Para obtener más información sobre la herencia de clases, incluido un ejemplo completo, vea about_Classes_Inheritance.

Uso de atributos de propiedad

PowerShell incluye varias clases de atributos que puede usar para mejorar la información del tipo de datos y validar los datos asignados a una propiedad. Los atributos de validación permiten probar que los valores proporcionados a las propiedades cumplen los requisitos definidos. La validación se desencadena en el momento en que se asigna el valor.

Para obtener más información sobre los atributos disponibles, consulte about_Functions_Advanced_Parameters.

Definición de propiedades de instancia con Update-TypeData

Más allá de declarar propiedades directamente en la definición de clase, puede definir propiedades para instancias de una clase en el constructor estático mediante el Update-TypeData cmdlet .

Use este fragmento de código como punto de partida para el patrón. Reemplace el texto del marcador de posición entre corchetes angulares según sea necesario.

class <ClassName> {
    static [hashtable[]] $MemberDefinitions = @(
        @{
            MemberName = '<PropertyName>'
            MemberType = '<PropertyType>'
            Value      = <ValueDefinition>
        }
    )

    static <ClassName>() {
        $TypeName = [<ClassName>].Name
        foreach ($Definition in [<ClassName>]::MemberDefinitions) {
            Update-TypeData -TypeName $TypeName @Definition
        }
    }
}

Sugerencia

El Add-Member cmdlet puede agregar propiedades y métodos a una clase en constructores no estáticos, pero el cmdlet se ejecuta cada vez que se llama al constructor. El uso Update-TypeData de en el constructor estático garantiza que el código para agregar los miembros a la clase solo debe ejecutarse una vez en una sesión.

Agregue solo propiedades a la clase en constructores no estáticos cuando no se puedan definir con Update-TypeData, como las propiedades de solo lectura.

Definición de propiedades de alias

El atributo Alias no tiene ningún efecto cuando se usa en una declaración de propiedad de clase. PowerShell solo usa ese atributo para definir alias para los nombres de cmdlet, parámetro y función.

Para definir un alias para una propiedad de clase, use Update-TypeData con AliasProperty MemberType.

Por ejemplo, esta definición de la clase OperablePair define dos propiedades de entero x e y con los alias LeftHandSide y RightHandSide respectivamente.

class OperablePair {
    [int] $x
    [int] $y

    static [hashtable[]] $MemberDefinitions = @(
            @{
                MemberType = 'AliasProperty'
                MemberName = 'LeftHandSide'
                Value      = 'x'
            }
            @{
                MemberType = 'AliasProperty'
                MemberName = 'RightHandSide'
                Value      = 'y'
            }
    )

    static OperablePair() {
        $TypeName = [OperablePair].Name
        foreach ($Definition in [OperablePair]::MemberDefinitions) {
            Update-TypeData -TypeName $TypeName @Definition
        }
    }

    OperablePair() {}

    OperablePair([int]$x, [int]$y) {
        $this.x = $x
        $this.y = $y
    }

    # Math methods for the pair of values
    [int]   GetSum()        { return $this.x + $this.y }
    [int]   GetProduct()    { return $this.x * $this.y }
    [int]   GetDifference() { return $this.x - $this.y }
    [float] GetQuotient()   { return $this.x / $this.y }
    [int]   GetModulus()    { return $this.x % $this.y }
}

Con los alias definidos, los usuarios pueden acceder a las propiedades con cualquier nombre.

$pair = [OperablePair]@{ x = 8 ; RightHandSide = 3 }

"$($pair.x) % $($pair.y) = $($pair.GetModulus())"

$pair.LeftHandSide  = 3
$pair.RightHandSide = 2
"$($pair.x) x $($pair.y) = $($pair.GetProduct())"
8 % 3 = 2

3 x 2 = 6

Definición de propiedades calculadas

Para definir una propiedad que haga referencia a los valores de otras propiedades, use el Update-TypeData cmdlet con ScriptProperty MemberType.

Por ejemplo, esta definición de la clase Budget define las propiedades Expenses e Revenues como matrices de números de punto flotante. Usa el Update-TypeData cmdlet para definir propiedades calculadas para gastos totales, ingresos totales y ingresos netos.

class Budget {
    [float[]] $Expenses
    [float[]] $Revenues

    static [hashtable[]] $MemberDefinitions = @(
        @{
            MemberType = 'ScriptProperty'
            MemberName = 'TotalExpenses'
            Value      = { ($this.Expenses | Measure-Object -Sum).Sum }
        }
        @{
            MemberType = 'ScriptProperty'
            MemberName = 'TotalRevenues'
            Value      = { ($this.Revenues | Measure-Object -Sum).Sum }
        }
        @{
            MemberType = 'ScriptProperty'
            MemberName = 'NetIncome'
            Value      = { $this.TotalRevenues - $this.TotalExpenses }
        }
    )

    static Budget() {
        $TypeName = [Budget].Name
        foreach ($Definition in [Budget]::MemberDefinitions) {
            Update-TypeData -TypeName $TypeName @Definition
        }
    }

    Budget() {}

    Budget($Expenses, $Revenues) {
        $this.Expenses = $Expenses
        $this.Revenues = $Revenues
    }
}

[Budget]::new()

[Budget]@{
    Expenses = @(2500, 1931, 3700)
    Revenues = @(2400, 2100, 4150)
}
TotalExpenses : 0
TotalRevenues : 0
NetIncome     : 0
Expenses      :
Revenues      :

TotalExpenses : 8131
TotalRevenues : 8650
NetIncome     : 519
Expenses      : {2500, 1931, 3700}
Revenues      : {2400, 2100, 4150}

Definición de propiedades con la lógica get y set personalizada

Las propiedades de clase de PowerShell no pueden definir directamente la lógica de captador y establecedor personalizada. Puede aproximarse a esta funcionalidad definiendo una propiedad de respaldo con la hidden palabra clave y usando Update-TypeData para definir una propiedad visible con lógica personalizada para obtener y establecer el valor.

Por convención, defina el nombre de propiedad de respaldo oculto con un prefijo de subrayado y use mayúsculas y minúsculas camel. Por ejemplo, en lugar de TaskCount, asigne un nombre a la propiedad _taskCountde respaldo oculta .

En este ejemplo, la clase ProjectSize define una propiedad entera oculta denominada _value. Define Value como con una ScriptProperty lógica personalizada para obtener y establecer la propiedad _value . El bloque de scripts establecedores controla la conversión de la representación de cadena del proyecto al tamaño correcto.

class ProjectSize {
    hidden [ValidateSet(0, 1, 2, 3)] [int] $_value

    static [hashtable[]] $MemberDefinitions = @(
        @{
            MemberType  = 'ScriptProperty'
            MemberName  = 'Value'
            Value       = { $this._value } # Getter
            SecondValue = {                # Setter
                $ProposedValue = $args[0]

                if ($ProposedValue -is [string]) {
                    switch ($ProposedValue) {
                        'Small'  { $this._value = 1 ; break }
                        'Medium' { $this._value = 2 ; break }
                        'Large'  { $this._value = 3 ; break }
                        default  { throw "Unknown size '$ProposedValue'" }
                    }
                } else {
                    $this._value = $ProposedValue
                }
            }
        }
    )

    static ProjectSize() {
        $TypeName = [ProjectSize].Name
        foreach ($Definition in [ProjectSize]::MemberDefinitions) {
            Update-TypeData -TypeName $TypeName @Definition
        }
    }

    ProjectSize()              {}
    ProjectSize([int]$Size)    { $this.Value = $Size }
    ProjectSize([string]$Size) { $this.Value = $Size }

    [string] ToString() {
        $Output = switch ($this._value) {
            1       { 'Small'     }
            2       { 'Medium'    }
            3       { 'Large'     }
            default { 'Undefined' }
        }

        return $Output
    }
}

Con el captador personalizado y el establecedor definidos, puede establecer la propiedad Value como un entero o una cadena.

$size = [ProjectSize]::new()
"The initial size is: $($size._value), $size"

$size.Value = 1
"The defined size is: $($size._value), $size"

$Size.Value += 1
"The updated size is: $($size._value), $size"

$Size.Value = 'Large'
"The final size is:   $($size._value), $size"
The initial size is: 0, Undefined

The defined size is: 1, Small

The updated size is: 2, Medium

The final size is:   3, Large

Limitaciones

Las propiedades de clase de PowerShell tienen las siguientes limitaciones:

  • Las propiedades estáticas siempre son mutables. Las clases de PowerShell no pueden definir propiedades estáticas inmutables.

    Solución alternativa: Ninguna.

  • Las propiedades no pueden usar el atributo ValidateScript , ya que los argumentos de atributo de propiedad de clase deben ser constantes.

    Solución alternativa: defina una clase que herede del tipo ValidateArgumentsAttribute y use ese atributo en su lugar.

  • Las propiedades declaradas directamente no pueden definir implementaciones personalizadas de captador y establecedor.

    Solución alternativa: defina una propiedad oculta y use Update-TypeData para definir la lógica de captador y establecedor visibles.

  • Las propiedades no pueden usar el atributo Alias . El atributo solo se aplica a parámetros, cmdlets y funciones.

    Solución alternativa: use el Update-TypeData cmdlet para definir alias en los constructores de clase.

  • Cuando una clase de PowerShell se convierte en JSON con el ConvertTo-Json cmdlet , el JSON de salida incluye todas las propiedades ocultas y sus valores.

    Solución alternativa: ninguna

Consulte también