Skip to content

Rewrote inner classes tour section #755

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
May 10, 2017

Conversation

travissarles
Copy link
Contributor

No description provided.

@travissarles travissarles requested a review from jarrodu March 31, 2017 13:11
@travissarles travissarles force-pushed the inner-classes branch 3 times, most recently from e7fd8fb to 9f8bfd3 Compare March 31, 2017 13:29
@jarrodu
Copy link
Member

jarrodu commented Mar 31, 2017

Hi Travis. I will take a look later today. At the moment I am UTC+2 in Hamburg but I should have some time later this evening.

Thanks for the contribution and talk to you soon.

@jarrodu
Copy link
Member

jarrodu commented Mar 31, 2017

Sorry not today. 😴 Tomorrow for sure.

Copy link
Member

@jarrodu jarrodu left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This seems like a few improvements that don't change the content of the entry. Any other comments I have are not blockers. They are only suggestions.

Thanks for the improvements.


We now enrich the above example with types to state explicitly what the type of the various defined entities is:

This program represents a graph as a list of nodes (`var nodes`). Each node knows which other nodes it's connected to (`connectedNodes`). The `class Node` is a _path-dependent type_ because it is nested in the `class Graph`. Therefore, everything in the `connectedNodes` must be created using the class attached to Graph.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The var in (var nodes) seems out of place.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I find "using the class attached to Graph" unclear, in my opinion — I'd suggest trying to find a clearer wording here, even if it requires using more words.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

agree on var nodes, I would expect to see e.g. List[Node] instead or whatever the actual type is


We now enrich the above example with types to state explicitly what the type of the various defined entities is:

This program represents a graph as a list of nodes (`var nodes`). Each node knows which other nodes it's connected to (`connectedNodes`). The `class Node` is a _path-dependent type_ because it is nested in the `class Graph`. Therefore, everything in the `connectedNodes` must be created using the class attached to Graph.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

"Each node knows which..." seems odd. Nodes don't know anything since they don't have thoughts. This would be like saying a chair knows that it has four legs.

@travissarles travissarles mentioned this pull request Apr 2, 2017
33 tasks
```

This code clearly shows that a node type is prefixed with its outer instance (which is object `g` in our example). If we now have two graphs, the type system of Scala does not allow us to mix nodes defined within one graph with the nodes of another graph, since the nodes of the other graph have a different type.
Notice how the type of all of the nodes is `graph1.Node`. This is because when we call `graph1.newNode` which calls `new Node`, the method is using the instance of `Node` specific to the instance `graph1`.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

After the "Notice how" sentence, perhaps insert: "We have explicitly supplied that type, but the compiler would infer it if we had left it out."

This code clearly shows that a node type is prefixed with its outer instance (which is object `g` in our example). If we now have two graphs, the type system of Scala does not allow us to mix nodes defined within one graph with the nodes of another graph, since the nodes of the other graph have a different type.
Notice how the type of all of the nodes is `graph1.Node`. This is because when we call `graph1.newNode` which calls `new Node`, the method is using the instance of `Node` specific to the instance `graph1`.

If we now have two graphs, the type system of Scala does not allow us to mix nodes defined within one graph with the nodes of another graph, since the nodes of the other graph have a different type.
Copy link
Member

@SethTisue SethTisue Apr 2, 2017

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is the key sentence of the entire article. I would suggest stating this very close to the beginning, rather than withholding it until the reader has had to wade through a lot of details.

So at the start, say something like "Suppose we want the compiler to prevent us, at compile time, from mixing up which nodes belong to what graph. Path-dependent types provide a solution."

Copy link
Member

@SethTisue SethTisue left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

otherwise ready for merge

@@ -11,7 +11,9 @@ next-page: abstract-types
previous-page: lower-type-bounds
---

In Scala it is possible to let classes have other classes as members. Opposed to Java-like languages where such inner classes are members of the enclosing class, in Scala such inner classes are bound to the outer object. To illustrate the difference, we quickly sketch the implementation of a graph datatype:
In Scala it is possible to let classes have other classes as members. Opposed to Java-like languages where such inner classes are members of the enclosing class, in Scala such inner classes are bound to the outer object. Suppose we want the compiler to prevent us, at compile time, from mixing up which nodes belong to what graph. Path-dependent types provide a solution.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

s/Opposed/As opposed/

@@ -31,7 +33,7 @@ class Graph {
}
}
```
This program represents a graph as a list of nodes (`var nodes`). Each node knows which other nodes it's connected to (`connectedNodes`). The `class Node` is a _path-dependent type_ because it is nested in the `class Graph`. Therefore, everything in the `connectedNodes` must be created using the class attached to Graph.
This program represents a graph as a list of nodes (`List[Node]`). Each node has a list of other nodes it's connected to (`connectedNodes`). The `class Node` is a _path-dependent type_ because it is nested in the `class Graph`. Therefore, all noes in the `connectedNodes` must be created using the `newNode` from the same instance of `Graph`.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

s/all noes/all nodes/

@travissarles travissarles merged commit ea9b5ad into scala:master May 10, 2017
@travissarles travissarles deleted the inner-classes branch May 10, 2017 13:00
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants