Skip to content
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

Questions about Blank Nodes #89

Open
tmciver opened this issue Jun 27, 2020 · 4 comments
Open

Questions about Blank Nodes #89

tmciver opened this issue Jun 27, 2020 · 4 comments

Comments

@tmciver
Copy link
Contributor

tmciver commented Jun 27, 2020

I see that there are two constructors for blank nodes: BNode and BNodeGen. When I use BNode (or bnode) and then serialize to Turtle, the blank nodes come through with names given by the text used to create them. Is this the intended behavior? I was expecting the more typical _:<identifier> format.

The doc string for BNodeGen says "An RDF blank node with an auto-generated identifier, as used in Turtle." but it does not seem get an auto-generated identifier; the identifier is simply _:genid prepended to the integer passed into the constructor. I would expect such a feature to not require passing in an integer and to create an identifier that the library ensured was unique within the given graph. Is that the intended behavior of BNodeGen? Is there some other way to create a blank node with an auto-generated ID as I describe?

@robstewart57
Copy link
Owner

Hi @tmciver and @koslambrou (from #106),

We have two options:

  1. Validate blank node labels in the bnode function e.g.
bnode "_:foo" => Just (BNode "_:foo")
bnode "foo"   => Nothing
bnode "_foo"  => Nothing
bnode ":foo"  => Nothing
  1. Generate a valid blank from an arbitrary label e.g.
bnode "foo" => BNode "_:foo"

The issue with the 2nd option is that the blank node label should be unique in a graph, but the bnode function is not associated with an RDF graph:

bnode :: Text -> Node

There could be a method added to the Rdf type class to associate bnode with graphs to allow option 2:

class (Generic rdfImpl, NFData rdfImpl) => Rdf rdfImpl where
   ...
   bnodeGen :: RDF rdfImpl -> Text -> (Node, RDF rdfImpl)

e.g. something like

let g1 = empty
let (n1, g2) = bnodeGen g1 "foo"
let (n2, g3) = bnodeGen g2 "foo"

where n1 == "_:foo1" and n2 == "_:foo2".

but this burdens all instances of Rdf so my instinct is to go for option 1 instead. The main limitation of option 1 is that the burden is on the programmer to ensure that blank node labels are unique, when used in triples added to an RDF graph.

Thoughts?

@koslambrou
Copy link
Contributor

@robstewart57 I don't mind option 1 with bnode. However, what about BNodeGen ? I doesn't seem to autogenerate a an identifier. Should it be removed ?

robstewart57 added a commit that referenced this issue Mar 28, 2021
@robstewart57
Copy link
Owner

@tmciver and @koslambrou

This is addressed in the bnodeGen branch. See this commit message: 3da3a9f

Thoughts?

@tmciver
Copy link
Contributor Author

tmciver commented Mar 28, 2021

I'd like to see a solution that guarantees blank node uniqueness for a given graph and so I'm in favor of the solution that adds a blank node creation function to the type class. But the sample code provided by @robstewart57:

let g1 = empty
let (n1, g2) = bnodeGen g1 "foo"
let (n2, g3) = bnodeGen g2 "foo"

suggests use of State or StateT which was also suggested by @koslambrou here. I like this solution as it solves the unique blank node issue as well as giving a nice interface for graph manipulation.

Thoughts on such a solution?

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

No branches or pull requests

3 participants