F # private class inside public

I have a Java class and I need to write a similar one in F #. How to define a private class inside public in f #?

public class KnownRuleGoals { void record() { knownParsingSet.add(new KnownParsing()); } private class KnownParsing { Rule [] knownParsing; KnownParsing() { ... } void doWork() { ... } } } 
+5
source share
2 answers

This is entirely possible in F #. F # is functional first, not purely functional - and this is one of its main strengths. F # is pragmatic, and this construction below allows you to achieve exactly the same result, even if the type KnownParsing not "nested" in the sense of Java or C #.

 type KnownRuleGoals() = let knownParsingSet : List<KnownParsing> = List() member this.Record() = knownParsingSet.Add(new KnownParsing()) and private KnownParsing() = let foo = "private fields" member this.DoWork() = failwith "TODO implementation" 

Object expressions are useful for implementing interfaces or abstract classes, but the β€œparent” class (the one that creates the object expression) will not be able to access its internals. Or rather, there is no way to create internal elements other than interface / abstract in any way, except through ref cells outside the object expression itself. This has performance implications, such as GC pressure for reflective cells.

See this example in my open source project on how object expressions and "nested through and" types work interchangeably to implement IEnumerator . For this line, I use the private type, as in this answer, and it works well. Throughout the project, I use F # mostly in an imperative way, because this is the only way to get decent performance. And I have to say that I like F # most often over C # even for imperative code.

+7
source

As people said, F # does not currently support nested classes.

One way around this, as shown by VB, is with two separate classes, one of which is private.

However, if the inner class is simple (with only one or two methods), then there is an alternative approach that should use closure as an object for poor people .

In the code below, the KnownParsing function creates two functions and returns them as a pair. knownParsingSet then contains function pairs, not class instances.

If there is only one method in a nested class, then this approach is great, because one method class is basically just a function. For more than one method in a nested class, it gets pretty ugly, which is why F # people have a problem using other methods. :)

 type KnownRuleGoals() = let knownParsingSet = System.Collections.Generic.HashSet() // use a function let KnownParsing() = let knownParsing = [||] let doWork() = () // do something let doWork2() = () // do something // return the pair of functions doWork,doWork2 // the member/method comes after the closure because // definitions must come before usage. member this.record() = knownParsingSet.Add(KnownParsing()) 
+5
source

Source: https://habr.com/ru/post/1241448/


All Articles