Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Extend enumerations types in F#

Another question related to F# feature called "Type extensions".

It seems impossible to extend enumerations in F#. I use C# Extensions Methods a lot for extending enums: add range validation logic, method that returns string representation etc.

Unfortunately it seems possible extend only discriminated union but impossible to extend simple enumerations:

1. Intrinsic extension

// CustomEnum.fs
module CustomEnumModule

type CustomEnum = 
    | Value1 = 1
    | Value2 = 2

// Trying to split definition of the enum
type CustomEnum with 
    | Value3 = 3

Error: "error FS0010: Unexpected symbol '|' in member definition"

2. Optional extension

// CustomEnumEx.fs
open CustomEnumModule

type CustomEnum with
    member public x.PrintValue() =
        printfn "%A" x

Error: "error FS0896: Enumerations cannot have members"

It seems weird for me because (1) we can treat simple enumerations as a special case of full-featured discriminated union and we can extend discriminated unions and (2) extending .NET enums is a good way to add some features (including FP-features) to existing infrastructure.

Is this behavior intentional or this is simple bug in implementation?

P.S. Unfortunately F# Spec is silent in this regard, or at least I can't find any proofs for one or another behavior there.

like image 896
Sergey Teplyakov Avatar asked Apr 06 '13 11:04

Sergey Teplyakov


People also ask

Can enum be extended C++?

No, there is not. enum are really the poor thing in C++, and that's unfortunate of course. Even the class enum introduced in C++0x does not address this extensibility issue (though they do some things for type safety at least).

Can an enum extend another enum C++?

Enum and has several static members. Therefore, enum cannot extend any other class or enum : there is no multiple inheritance. Class cannot extend enum , as well. This limitation is enforced by the compiler.

What are enum types?

Enumerated (enum) types are data types that comprise a static, ordered set of values. They are equivalent to the enum types supported in a number of programming languages. An example of an enum type might be the days of the week, or a set of status values for a piece of data.

Can you extend an enum C#?

Since it's not a class, it cannot be extended and its defined values are limited to a small set of primitive types ( byte , sbyte , short , ushort , int , uint , long , ulong ). For instance, sometimes it is very convenient to get the list of enum values and display it in a combobox.


1 Answers

It is possible to create a module with the same name as a type which is similar to extending the type:

type CustomEnum = Value1 = 1 | Value2 = 2

[<CompilationRepresentation(CompilationRepresentationFlags.ModuleSuffix)>]
module CustomEnum =
    let Print = function
    | CustomEnum.Value1 -> "One"
    | CustomEnum.Value2 -> "Two"
    | _ -> invalidArg "" ""

let value = CustomEnum.Value1

let s = CustomEnum.Print value
like image 163
Phillip Trelford Avatar answered Oct 19 '22 03:10

Phillip Trelford