SPAQRL: select item and count occurences of its label - duplicates

I have this SPARQL query directed to the Open Research Knowledge Graph (ORKG):
PREFIX orkgr: <http://orkg.org/orkg/resource/>
PREFIX orkgc: <http://orkg.org/orkg/class/>
PREFIX orkgp: <http://orkg.org/orkg/predicate/>
PREFIX rdfs: <http://www.w3.org/2000/01/rdf-schema#>
PREFIX xsd: <http://www.w3.org/2001/XMLSchema#>
PREFIX rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#>
SELECT ?o1Label (COUNT(?o1Label) AS ?o1LabelCount)
WHERE {
?o1 a orkgc:Paper.
?o1 rdfs:label ?o1Label.
FILTER (strlen(?o1Label) > 1).
}
GROUP BY ?o1Label
ORDER BY DESC(?o1LabelCount)
Which results in labels (?o1Label) and the number of occurrences of this label (?o1LabelCount).
How can I extend this query to also include a column for the actual item (?o1)?
Because there might be multiple candidates (when o1LabelCount is > 1), there should be one row for each of these items (with the same label and the same label count).

I see two options:
First (and probably better) is to use GROUP_CONCAT and collect the entities into one field to be parsed again on application side. this could look like this (link):
PREFIX orkgr: <http://orkg.org/orkg/resource/>
PREFIX orkgc: <http://orkg.org/orkg/class/>
PREFIX orkgp: <http://orkg.org/orkg/predicate/>
PREFIX rdfs: <http://www.w3.org/2000/01/rdf-schema#>
PREFIX xsd: <http://www.w3.org/2001/XMLSchema#>
PREFIX rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#>
SELECT ?o1Label (GROUP_CONCAT(?o1, "\t") AS ?o1s) (COUNT(?o1Label) AS ?o1LabelCount)
WHERE {
?o1 a orkgc:Paper.
?o1 rdfs:label ?o1Label.
FILTER (strlen(?o1Label) > 1).
}
GROUP BY ?o1Label
ORDER BY DESC(?o1LabelCount)
An alternative would be using nested queries and receive a result as you described (link):
PREFIX orkgr: <http://orkg.org/orkg/resource/>
PREFIX orkgc: <http://orkg.org/orkg/class/>
PREFIX orkgp: <http://orkg.org/orkg/predicate/>
PREFIX rdfs: <http://www.w3.org/2000/01/rdf-schema#>
PREFIX xsd: <http://www.w3.org/2001/XMLSchema#>
PREFIX rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#>
SELECT ?o1Label ?o1 ?o1LabelCount
WHERE {
?o1 rdfs:label ?o1Label .
{
SELECT ?o1Label (COUNT(?o1Label) AS ?o1LabelCount)
WHERE {
[
a orkgc:Paper;
rdfs:label ?o1Label
]
FILTER (strlen(?o1Label) > 1).
}
}
}
GROUP BY ?o1Label
ORDER BY DESC(?o1LabelCount)

Related

Laravel SQL parameter bindings when using raw sql

I have the following query:
$venues = Venue::select(['id', 'name'])
->where('name', 'LIKE', "%{$query}%")
->orderByRaw("CASE " .
"WHEN name like '{$query}%' THEN 0 " . // start with
"WHEN name like '% {$query}%' THEN 1 " . // start of a later word
"ELSE 3 " .
"END"
)
->limit(5)
->get();
The issue is the above query is vulnerable to SQL injection.
How can I fix this?
Parameter bindings is explained here:
https://laravel.com/docs/5.6/queries#raw-expressions
But if I do:
$venues = Venue::select(['id', 'name'])
->where('name', 'LIKE', "%{$query}%")
->orderByRaw("CASE " .
"WHEN name like '?%' THEN 0 " . // start with
"WHEN name like '% ?%' THEN 1 " . // start of a later word
"ELSE 3 " .
"END",
[
$query,
$query,
]
)
->limit(5)
->get();
I get different results.
Try adding the percent to the query param, like this:
...
->orderByRaw("CASE " .
"WHEN name like ? THEN 0 " . // start with
"WHEN name like ? THEN 1 " . // start of a later word
"ELSE 3 " .
"END",
[
"{$query}%",
"% {$query}%",
]
)
...

Haskell function composition methods

I just started learning Haskell at uni, and while playing around with it, I stumbled upon a problem that I can't seem to grasp.
The following code gives me the desired result:
import Data.List
list = ["Hello", "world"]
main = print $ intercalate " something " (reverse (map reverse list))
Output:
"dlrow something olleH"
But I want to write the 'main' function with dots instead of brackets, so it tried:
main = print $ intercalate " something " . reverse . map reverse list
However, this gives me the following errors:
test.hs:5:54: error:
• Couldn't match expected type ‘a0 -> [[Char]]’
with actual type ‘[[Char]]’
• Possible cause: ‘map’ is applied to too many arguments
I thought that these dots meant exactly the same as the brackets: function composition. Why do the brackets work, whereas the dots give me a type-related error? Any help would be greatly appreciated!
Brackets don't mean function composition. They just mean “group this subexpression”. Of course you can use them to make a chain of function compositions: the following defines c as a composition of the functions f, g and h
c x = f (g (h x))
This could also be written as:
c = f . g . h
Thus, you could write
main = print $ c list
where c = intercalate " something " . reverse . map reverse
But if you then inline c again, you need to be careful not to mess up the parsing rules: just writing list to the right of that composition chain will not do, because function application binds more tightly than any infix operator (including ., though that is in fact the tightest infix operator). I.e.,
intercalate " something " . reverse . map reverse list
is actually parsed as
(intercalate " something ") . (reverse) . (map reverse list)
But that's not what you wanted. You need to make sure that list is actually the argument to the entire composition chain, not just its last element; the preferred way to do that is with the $ operator:
intercalate " something " . reverse . map reverse $ list
$ has the lowest prevedence, thus this is parsed as
((intercalate " something ") . (reverse) . (map reverse)) (list)
Alternatively, you can apply map reverse to list right away – this by itself isn't wrong, just the result isn't part of the composition chain anymore:
intercalate " something " . reverse $ map reverse list
The equivalence of function composition goes as follows:
main = print (intercalate " something " (reverse (map reverse list)))
main = print (intercalate " something " ((reverse . map reverse) list))
main = print ((intercalate " something " . (reverse . map reverse)) list)
main = (print . (intercalate " something " . (reverse . map reverse))) list
or, by dropping the unnecessary parentheses:
main = (print . intercalate " something " . reverse . map reverse) list
main = print . intercalate " something " . reverse . map reverse $ list
In your attempt, map reverse list is a single expression, the argument of the infix . operator, which doesn't work - you only can compose the map reverse function, and then apply the whole composed function to the list argument.
Function composition using . implies that there will be another parameter to the function. Had you instead written the following, it would work.
main = print $ (intercalate " something " . reverse . map reverse) list
That way, the list value is a parameter to the function composed inside parentheses.

publishing RDF (Turtle) using linked data Principles

I have following RDF (Turtle) file, this RDF is generated from CSV file using CSV2RDF conversion process by java language. I need to publish this RDF file on the web using linked data principles. How can i publish this RDF data on the web? thanks
#prefix rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#> .
#prefix rdfs: <http://www.w3.org/2000/01/rdf-schema#> .
#prefix csvw: <http://www.w3.org/ns/csvw#> .
#prefix dc: <http://purl.org/dc/elements/1.1/> .
#prefix dcat: <http://www.w3.org/ns/dcat#> .
#prefix foaf: <http://xmlns.com/foaf/0.1/> .
#prefix schema: <http://schema.org/> .
#prefix xsd: <http://www.w3.org/2001/XMLSchema#> .
<_:G> a csvw:TableGroup ;
csvw:table <_:table0> .
<_:table0> a csvw:Table ;
csvw:url <file:///D:\\Junhua\\10.5.2016 prototype\\tree-ops - Copy.csv> ;
csvw:row <_:row0> .
<_:row0> a csvw:Row ;
csvw:rownum "1"^^xsd:int ;
csvw:url <file:///D:\\Junhua\\10.5.2016 prototype\\tree-ops - Copy.csv#row=2> ;
csvw:describes <_:sDef0> .
<_:sDef0> <_:col[0]> "Ming" ;
<_:col[1]> "Professor" ;
<_:col[2]> "Celtis australis" ;
<_:col[3]> "10k" ;
<_:col[4]> "Software Engineering" .
<_:table0> csvw:row <_:row1> .
<_:row1> a csvw:Row ;
csvw:rownum "2"^^xsd:int ;
csvw:url <file:///D:\\Junhua\\10.5.2016 prototype\\tree-ops - Copy.csv#row=3> ;
csvw:describes <_:sDef1> .
<_:sDef1> <_:col[0]> "Tang" ;
<_:col[1]> "Lecturer" ;
<_:col[2]> "Liquidambar styraciflua" ;
<_:col[3]> "5k" ;
<_:col[4]> "Database Management" .
<_:table0> csvw:row <_:row2> .
<_:row2> a csvw:Row ;
csvw:rownum "3"^^xsd:int ;
csvw:url <file:///D:\\Junhua\\10.5.2016 prototype\\tree-ops - Copy.csv#row=4> ;
csvw:describes <_:sDef2> .
<_:sDef2> <_:col[0]> "Fang" ;
<_:col[1]> "Assistant Professor" ;
<_:col[2]> "Bangla text" ;
<_:col[3]> "7k" ;
<_:col[4]> "Semantic Management" .
You may want to read the Best Practices document.
Off the top of my head you should tweak your conversion process:
Eliminate some of the blank nodes, so that the data can be retrieved over the web. Hash URIs would be a good choice
file:/// URIs are also no good, because they are meaningless for external consumers
You should include some links to other datasets like DBpedia or Wikidata. The links are what defines Linked Data
Finally, for starters the publishing itself could be as simple as putting your turtle as static content file.

Fuseki on OpenShift: Can UPDATE but not SELECT

I have installed a Jena Fuseki server on OpenShift.
The --config services.ttl configuration file is as shown below.
What I observe is the following:
If I perform a SPARQL update from the Control Panel I get Update Succeeded and some TDB files do change on the server (in ./app-root/data/DB/).
However when I perform a SPARQL query such as SELECT ?s ?p ?o WHERE { ?s ?p ?o. } again in the Control Panel I get zero statements back. This same is true for this GET request:
http://<obfuscated>.rhcloud.com/ds/query?query=SELECT+%3Fs+%3Fp+%3Fo+WHERE+{+%3Fs+%3Fp+%3Fo.+}&output=text&stylesheet=
The log file on OpenShift contains these entries:
INFO [24] GET http://<obfuscated>.rhcloud.com/ds/query?query=SELECT+%3Fs+%3Fp+%3Fo+WHERE+{+%3Fs+%3Fp+%3Fo.+}+&output=text&stylesheet=
INFO [24] Query = SELECT ?s ?p ?o WHERE { ?s ?p ?o. }
INFO [24] exec/select
INFO [24] 200 OK (2 ms)
So it appears as if RDF statements can be written to TDB but not retrieved. If I try the same on a local installation of Fuseki the problem does not manifest.
What else can I do to diagnose and resolve this problem with Fuseki on OpenShift?
UPDATE Apparently the problem does not manifest if I INSERT statements into a named GRAPH (not the default graph).
#prefix : <#> .
#prefix fuseki: <http://jena.apache.org/fuseki#> .
#prefix rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#> .
#prefix rdfs: <http://www.w3.org/2000/01/rdf-schema#> .
#prefix tdb: <http://jena.hpl.hp.com/2008/tdb#> .
#prefix ja: <http://jena.hpl.hp.com/2005/11/Assembler#> .
[] rdf:type fuseki:Server ;
fuseki:services (
<#service>
) .
[] ja:loadClass "com.hp.hpl.jena.tdb.TDB" .
tdb:DatasetTDB rdfs:subClassOf ja:RDFDataset .
tdb:GraphTDB rdfs:subClassOf ja:Model .
<#service> a fuseki:Service ;
fuseki:name "ds" ;
fuseki:serviceQuery "sparql" ;
fuseki:serviceQuery "query" ;
fuseki:serviceUpdate "update" ;
fuseki:serviceUpload "upload" ;
fuseki:serviceReadWriteGraphStore "data" ;
fuseki:dataset <#dataset> ;
.
<#dataset> a tdb:DatasetTDB ;
tdb:location "../data/DB" ;
tdb:unionDefaultGraph true ;
.
tdb:unionDefaultGraph true turned out to be the culprit. From the documentation:
An assembler can specify that the default graph for query is the union
of the named graphs. This is done by adding tdb:unionDefaultGraph.
Since this does not mention the default graph as part of the union I guess with this configuration there is no default graph other than the union of the named graph and hence updates that do not name a graph are ignored.
The described problem disappears with the alternative configuration tdb:unionDefaultGraph false.

If JSON contains $myid then (Perl)

I'm trying to loop through JSON:
my $cards = $json_obj->decode( $jsoncards->content );
foreach my $card ( #$cards )
{
print Dumper $card->{idMembers};
if ( $card->{idMembers} =~ $myid )
{
print $card->{name} . "\n";
}
}
The output from print Dumper $card->{idMembers}; is:
$VAR1 = [
'50e442a195105cde670743e4',
'50fd66804825017002070285',
'50f71f02a30d2a8c0d07d10d'
];
How do I compare to those ids?
The bind operator =~ treats its LHS as a string and the RHS as a pattern. The stringification of an arrayref looks like ARRAY(0x12ABF14), so this isn't useful.
We have two possibilities to match the $myid against each member of the array:
The grep EXPR, LIST builtin. Selects all elements where the expression returns a true value. If the count of the returned items is ≥ 1, then a matching element was found.
if ( grep $myid eq $_, #{ $card->{idMembers} }) { do stuff }
# or: grep /\Q$myid/, ... if you don't want string equality
Use the smartmatch operator ~~ in the member-of meaning:
if ( $myid ~~ $card->{idMembers} ) { do stuff }
This is subjects to multiple caveats: (1) It is only usable since v10.1. Therefore, code using smartmatch should at least use 5.010001. (2) Smartmatch was re-labeled as experimental in the latest release of perl, and may change without much notice. (3) If the idMembers entry is not an array, smartmatch may hide the error.
Smartmatch depends on the type of both operands. If you want to select all entries that contain $myid as a substring, you should probably pass it as a regex object: qr/\Q$myid/ ~~ .... Otherwise, it will likely test for equality