rtm 0.1.6 → 0.2
Sign up to get free protection for your applications and to get access to all the features.
- data/DISCLAIMER +10 -33
- data/LICENSE +201 -0
- data/README +32 -3
- data/lib/rtm.rb +126 -74
- data/lib/rtm/axes.rb +298 -0
- data/lib/rtm/axes/association.rb +76 -0
- data/lib/rtm/axes/associations.rb +96 -0
- data/lib/rtm/axes/assocs_names_occs.rb +56 -0
- data/lib/rtm/axes/characteristic.rb +68 -0
- data/lib/rtm/axes/characteristics.rb +93 -0
- data/lib/rtm/axes/string.rb +76 -0
- data/lib/rtm/axes/strings.rb +87 -0
- data/lib/rtm/axes/topic.rb +233 -0
- data/lib/rtm/axes/topics.rb +280 -0
- data/lib/rtm/{backward_compatibility.rb → deprecated/index_property_set.rb} +3 -0
- data/lib/rtm/engine.rb +101 -0
- data/lib/rtm/extensions.rb +65 -5
- data/lib/rtm/{locator_helpers.rb → helpers/locator.rb} +15 -4
- data/lib/rtm/{helpers.rb → helpers/no_output.rb} +3 -0
- data/lib/rtm/helpers/uri.rb +13 -0
- data/lib/rtm/io.rb +19 -0
- data/lib/rtm/io/from_xtm2_libxml.rb +2 -1
- data/lib/rtm/io/tmapix_from.rb +155 -0
- data/lib/rtm/io/tmapix_to.rb +223 -0
- data/lib/rtm/io/to_hash.rb +154 -0
- data/lib/rtm/io/to_jtm.rb +53 -103
- data/lib/rtm/io/to_rdf.rb +45 -0
- data/lib/rtm/io/to_string.rb +21 -8
- data/lib/rtm/io/to_xtm1.rb +6 -4
- data/lib/rtm/io/to_xtm2.rb +10 -8
- data/lib/rtm/io/to_yaml.rb +59 -100
- data/lib/rtm/navigation.rb +23 -0
- data/lib/rtm/navigation/association/players.rb +25 -0
- data/lib/rtm/navigation/name/atomify.rb +19 -0
- data/lib/rtm/navigation/name/characteristics.rb +33 -0
- data/lib/rtm/navigation/occurrence/atomify.rb +19 -0
- data/lib/rtm/navigation/occurrence/characteristics.rb +33 -0
- data/lib/rtm/navigation/topic/characteristics.rb +33 -0
- data/lib/rtm/navigation/topic/indicators.rb +31 -0
- data/lib/rtm/navigation/topic/items.rb +31 -0
- data/lib/rtm/navigation/topic/locators.rb +31 -0
- data/lib/rtm/navigation/topic/players.rb +27 -0
- data/lib/rtm/navigation/topic/supertypes.rb +166 -0
- data/lib/rtm/navigation/topic/traverse.rb +51 -0
- data/lib/rtm/navigation/topic/types.rb +109 -0
- data/lib/rtm/psi.rb +39 -2
- data/lib/rtm/sugar.rb +47 -0
- data/lib/rtm/sugar/association/hash_access.rb +46 -0
- data/lib/rtm/sugar/occurrence/dynamic_value.rb +58 -0
- data/lib/rtm/sugar/occurrence/external.rb +53 -0
- data/lib/rtm/sugar/reifiable/reifier.rb +21 -0
- data/lib/rtm/sugar/role/counterparts.rb +139 -46
- data/lib/rtm/sugar/topic/best_name.rb +74 -0
- data/lib/rtm/sugar/topic/characteristics.rb +126 -12
- data/lib/rtm/sugar/topic/counterparts.rb +145 -10
- data/lib/rtm/sugar/topic/hash_access.rb +140 -30
- data/lib/rtm/sugar/topic/scoped.rb +114 -0
- data/lib/rtm/sugar/topic/topic_ref.rb +86 -0
- data/lib/rtm/sugar/topic/typed.rb +207 -0
- data/lib/rtm/sugar/topic_map/query_cache.rb +66 -0
- data/lib/rtm/sugar/topic_map/themes.rb +53 -0
- data/lib/rtm/sugar/typed/types.rb +38 -0
- data/lib/rtm/validation.rb +7 -4
- data/lib/rtm/version.rb +30 -0
- data/spec/helpers/spec_exampleexamplegroup.rb +14 -0
- data/spec/rtm/axes/association_spec.rb +88 -0
- data/spec/rtm/axes/associations_spec.rb +60 -0
- data/spec/rtm/axes/assocs_names_occs_spec.rb +9 -0
- data/spec/rtm/axes/characteristic_spec.rb +90 -0
- data/spec/rtm/axes/characteristics_spec.rb +85 -0
- data/spec/rtm/axes/string_spec.rb +145 -0
- data/spec/rtm/axes/strings_spec.rb +168 -0
- data/spec/rtm/axes/topic_spec.rb +124 -0
- data/spec/rtm/axes/topics_spec.rb +103 -0
- data/spec/rtm/base_spec.rb +32 -0
- data/spec/rtm/io/tmapix_from_spec.rb +76 -0
- data/spec/rtm/io/tmapix_to_spec.rb +159 -0
- data/spec/rtm/io/to_hash_spec.rb +90 -0
- data/spec/rtm/io/to_rdf_spec.rb +37 -0
- data/spec/rtm/io/to_string_spec.rb +122 -0
- data/spec/rtm/io/to_yaml_spec.rb +89 -0
- data/spec/rtm/navigation/association/players_spec.rb +58 -0
- data/spec/rtm/navigation/association_spec.rb +52 -0
- data/spec/rtm/navigation/name/atomify_spec.rb +27 -0
- data/spec/rtm/navigation/name/characteristics_spec.rb +34 -0
- data/spec/rtm/navigation/name_spec.rb +52 -0
- data/spec/rtm/navigation/occurrence/atomify_spec.rb +27 -0
- data/spec/rtm/navigation/occurrence/characteristics_spec.rb +34 -0
- data/spec/rtm/navigation/occurrence_spec.rb +52 -0
- data/spec/rtm/navigation/string_spec.rb +51 -0
- data/spec/rtm/navigation/topic/characteristics_spec.rb +55 -0
- data/spec/rtm/navigation/topic/indicators_spec.rb +43 -0
- data/spec/rtm/navigation/topic/items_spec.rb +44 -0
- data/spec/rtm/navigation/topic/locators_spec.rb +44 -0
- data/spec/rtm/navigation/topic/players_spec.rb +48 -0
- data/spec/rtm/navigation/topic/scope_spec.rb +41 -0
- data/spec/rtm/navigation/topic/supertypes_spec.rb +376 -0
- data/spec/rtm/navigation/topic/traverse_spec.rb +64 -0
- data/spec/rtm/navigation/topic/types_spec.rb +195 -0
- data/spec/rtm/navigation/topic_spec.rb +153 -0
- data/spec/rtm/sugar/association/hash_access_spec.rb +55 -0
- data/spec/rtm/sugar/occurrence/dynamic_value_spec.rb +171 -0
- data/spec/rtm/sugar/occurrence/external_spec.rb +129 -0
- data/spec/rtm/sugar/reifiable/reifier_spec.rb +41 -0
- data/spec/rtm/sugar/role/counterparts_spec.rb +193 -0
- data/spec/rtm/sugar/topic/best_name_spec.rb +25 -0
- data/spec/rtm/sugar/topic/characteristics_spec.rb +333 -0
- data/spec/rtm/sugar/topic/counterparts_spec.rb +224 -0
- data/spec/rtm/sugar/topic/hash_access_spec.rb +234 -0
- data/spec/rtm/sugar/topic/scoped_spec.rb +195 -0
- data/spec/rtm/sugar/topic/topic_ref_spec.rb +44 -0
- data/spec/rtm/sugar/topic/typed_spec.rb +217 -0
- data/spec/rtm/sugar/topic_map/themes_spec.rb +67 -0
- data/spec/rtm/sugar/typed/types_spec.rb +24 -0
- data/spec/rtm/tmapi/core/association_spec.rb +169 -0
- data/spec/rtm/tmapi/core/construct_spec.rb +25 -0
- data/spec/rtm/tmapi/core/datatype_aware_spec.rb +236 -0
- data/spec/rtm/tmapi/core/name_spec.rb +270 -0
- data/spec/rtm/tmapi/core/occurrence_spec.rb +53 -0
- data/spec/rtm/tmapi/core/reifiable_spec.rb +168 -0
- data/spec/rtm/tmapi/core/role_spec.rb +73 -0
- data/spec/rtm/tmapi/core/scoped_spec.rb +441 -0
- data/spec/rtm/tmapi/core/topic_map_spec.rb +716 -0
- data/spec/rtm/tmapi/core/topic_spec.rb +1468 -0
- data/spec/rtm/tmapi/core/typed_spec.rb +112 -0
- data/spec/rtm/tmapi/core/variant_spec.rb +52 -0
- data/spec/rtm/tmapi/ext/java_util_set_spec.rb +34 -0
- data/spec/rtm/tmapi_spec.rb +44 -0
- data/spec/rtm/utils/sparql_spec.rb +26 -0
- data/spec/rtm_spec.rb +93 -0
- data/spec/spec_helper.rb +28 -0
- data/test/javalibs/junit-4.5.jar +0 -0
- data/test/javalibs/tmapi-2.0-tests.jar +0 -0
- data/test/tmapi_tests.rb +25 -0
- metadata +169 -65
- data/COPYRIGHT +0 -4
- data/lib/Rakefile.rb +0 -42
- data/lib/activetopicmaps.rb +0 -278
- data/lib/rtm/backend/active_record.rb +0 -58
- data/lib/rtm/backend/active_record/001_initial_schema.rb +0 -116
- data/lib/rtm/backend/active_record/association_and_role.rb +0 -33
- data/lib/rtm/backend/active_record/locators.rb +0 -55
- data/lib/rtm/backend/active_record/name_variant_occurrence.rb +0 -45
- data/lib/rtm/backend/active_record/quaaxtm2rtm.rb +0 -113
- data/lib/rtm/backend/active_record/quaaxtm2rtmviews.rb +0 -134
- data/lib/rtm/backend/active_record/set_wrapper.rb +0 -98
- data/lib/rtm/backend/active_record/tm_construct.rb +0 -62
- data/lib/rtm/backend/active_record/tm_delegator.rb +0 -345
- data/lib/rtm/backend/active_record/tm_set_delegator.rb +0 -195
- data/lib/rtm/backend/active_record/tmdm.rb +0 -298
- data/lib/rtm/backend/active_record/topic.rb +0 -87
- data/lib/rtm/backend/active_record/topic_map.rb +0 -314
- data/lib/rtm/backend/active_record/traverse_associations.rb +0 -87
- data/lib/rtm/base.rb +0 -92
- data/lib/rtm/connect.rb +0 -92
- data/lib/rtm/core_ext.rb +0 -6
- data/lib/rtm/io/from_xtm2.rb +0 -263
- data/lib/rtm/merging/merging.rb +0 -307
- data/lib/rtm/pimp_my_api.rb +0 -28
- data/lib/rtm/sugar/topic/identifier_direct.rb +0 -11
- data/lib/rtm/sugar/topic/predefined_associations.rb +0 -42
- data/lib/run_main_project.rb +0 -16
- data/test/base_test.rb +0 -162
@@ -0,0 +1,74 @@
|
|
1
|
+
# Copyright: Copyright 2009 Topic Maps Lab, University of Leipzig.
|
2
|
+
# License: Apache License, Version 2.0
|
3
|
+
|
4
|
+
module RTM::Sugar::Topic::BestName
|
5
|
+
|
6
|
+
# Tries to find the best matching name for a given topic.
|
7
|
+
#
|
8
|
+
def best_name (theme = nil)
|
9
|
+
all_names = self.names
|
10
|
+
|
11
|
+
# return last part of identifier if no name exist
|
12
|
+
return find_user_friendly_identifier(self) if all_names.empty
|
13
|
+
|
14
|
+
# collect name with default name type
|
15
|
+
default_names = []
|
16
|
+
all_names.each do |name|
|
17
|
+
type_of_name = name.getType
|
18
|
+
|
19
|
+
next if type_of_name.nil?
|
20
|
+
type_identifiers = type_of_name.subject_identifiers.to_a
|
21
|
+
|
22
|
+
type_identifiers.each do |i|
|
23
|
+
if i.toExternalForm == RTM::PSI[:name_type] then
|
24
|
+
default_names << name
|
25
|
+
break
|
26
|
+
end
|
27
|
+
end
|
28
|
+
end
|
29
|
+
|
30
|
+
default_names = all_names if default_names.empty?
|
31
|
+
default_names = default_names.select { |name| not name.scope.to_a.index(theme).nil? } if not theme.nil?
|
32
|
+
default_names = all_names if default_names.empty?
|
33
|
+
|
34
|
+
# get default name with the minimum number of scopes
|
35
|
+
min_scoped_name = default_names.sort_by{|n| n.value}.min {|n1,n2| n1.getScope.size <=> n2.getScope.size}
|
36
|
+
min_scoped_name.value
|
37
|
+
end
|
38
|
+
|
39
|
+
private
|
40
|
+
def find_user_friendly_identifier(topic)
|
41
|
+
return psi_prefix topic.
|
42
|
+
subject_identifiers.
|
43
|
+
sort_by{|sid| sid.value.length}.
|
44
|
+
first.
|
45
|
+
value unless topic.subject_identifiers.empty?
|
46
|
+
|
47
|
+
return topic.
|
48
|
+
topic_references.
|
49
|
+
map{|sid| sid.gsub /^[\^=]/, ''}.
|
50
|
+
sort_by{|sid| sid.length }.
|
51
|
+
first
|
52
|
+
|
53
|
+
# fallback
|
54
|
+
return create_shortest_topic_identifier topic
|
55
|
+
end
|
56
|
+
|
57
|
+
def create_shortest_topic_identifier(topic)
|
58
|
+
base_iri = topic.topic_map.base_locator
|
59
|
+
|
60
|
+
topic.getItemIdentifiers.each do |item_identifier|
|
61
|
+
iid_iri = item_identifier.value
|
62
|
+
iid_iri.scan(/(file:)?\/*#{base_iri}#(.*)/) { |pair| return "^#{pair[1]}" }
|
63
|
+
end
|
64
|
+
|
65
|
+
CGI::escape(topic.topic_references.sort_by { |reference| reference.length }.first.to_s)
|
66
|
+
|
67
|
+
# throw('Unable to create simplified identifier from topic.', topic)
|
68
|
+
end
|
69
|
+
|
70
|
+
# HACK
|
71
|
+
def psi_prefix(name)
|
72
|
+
name.gsub /^http\:\/\/psi\.topicmaps\.org\/iso13250\/model\//, 'tmdm:'
|
73
|
+
end
|
74
|
+
end
|
@@ -1,15 +1,129 @@
|
|
1
|
-
|
2
|
-
|
3
|
-
|
4
|
-
|
5
|
-
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
|
10
|
-
|
11
|
-
|
12
|
-
|
1
|
+
# Copyright: Copyright 2009 Topic Maps Lab, University of Leipzig.
|
2
|
+
# License: Apache License, Version 2.0
|
3
|
+
|
4
|
+
module RTM::Sugar::Topic::Characteristics
|
5
|
+
|
6
|
+
# Returns all Occurrences of this Topic whose datatype is not IRI
|
7
|
+
#
|
8
|
+
# :call-seq:
|
9
|
+
# internal_occurrences -> Set of Occurrences
|
10
|
+
#
|
11
|
+
def internal_occurrences
|
12
|
+
occurrences.select{|x| x.getDatatype.toExternalForm != RTM::PSI[:IRI]}
|
13
|
+
end
|
14
|
+
|
15
|
+
# Returns all Occurrences of this Topic whose datatype is IRI
|
16
|
+
#
|
17
|
+
# :call-seq:
|
18
|
+
# external_occurrences -> Set of Occurrences
|
19
|
+
#
|
20
|
+
def external_occurrences
|
21
|
+
occurrences.select{|y| y.getDatatype.toExternalForm == RTM::PSI[:IRI]}
|
22
|
+
end
|
23
|
+
|
24
|
+
# Returns the names of this topic which may be filtered for their type,
|
25
|
+
# value and/or scope.
|
26
|
+
#
|
27
|
+
# If scope is set to :ucs, names which exist in the unconstrained scope
|
28
|
+
# are selected. If scope is set to :any (default), scope does not constrain
|
29
|
+
# the names-Array. Else, only the names which whose scope contains one of the
|
30
|
+
# given themes are returned.
|
31
|
+
#
|
32
|
+
# Returns an empty Array if no names match or if the name type
|
33
|
+
# or scope does not exist.
|
34
|
+
#
|
35
|
+
# :call-seq:
|
36
|
+
# names_by -> Array of Names
|
37
|
+
# names_by(:type => identifier) -> Array of Names
|
38
|
+
# names_by(:value => string) -> Array of Names
|
39
|
+
# names_by(:scope => identifier) -> Array of Names
|
40
|
+
# names_by(:type => identifier, :value => string) -> Array of Names
|
41
|
+
# names_by(:type => identifier, :value => string, :scope => identifier) -> Array of Names
|
42
|
+
# and so on
|
43
|
+
#
|
44
|
+
def names_by(args = {})
|
45
|
+
raise("names_by: arguments must be a Hash") unless args.is_a?(Hash)
|
46
|
+
default_hash = {:type => :any, :value => :any, :scope => :any}
|
47
|
+
args = default_hash.merge(args)
|
48
|
+
#filter for type
|
49
|
+
_names = args[:type] == :any ? names : names(args[:type])
|
50
|
+
_names = self.filter_by(_names,args)
|
51
|
+
# return Array
|
52
|
+
return _names.to_a
|
53
|
+
end
|
54
|
+
|
55
|
+
# Returns Occurrences of this Topic which may be filtered for their type,
|
56
|
+
# value, datatype and/or scope.
|
57
|
+
#
|
58
|
+
# If scope is set to :ucs, Occurrences which exist in the unconstrained scope
|
59
|
+
# are selected. If scope is set to :any (default), scope does not constrain
|
60
|
+
# the Occurrence-Array. Else, only the occurrences which whose scope contains
|
61
|
+
# one of the given themes are returned.
|
62
|
+
#
|
63
|
+
# Returns an empty Array if no Occurrences match or if the Occurrence type or
|
64
|
+
# scope does not exist.
|
65
|
+
#
|
66
|
+
# :call-seq:
|
67
|
+
# occurrence_by -> Array of Occurrences
|
68
|
+
# occurrences_by(:type => argument) -> Array of Occurrences
|
69
|
+
# occurrences_by(:value => argument) -> Array of Occurrences
|
70
|
+
# occurrences_by(:scope => argument) -> Array of Occurrences
|
71
|
+
# occurrences_by(:datatype => argument) -> Array of Occurrences
|
72
|
+
# occurrences_by(:type => argument1, :value => argument2) -> Array of Occurrences
|
73
|
+
# occurrences_by(:type => argument1, :value => argument2, :scope => argument3, :datatype => argument4) -> Array of Occurrences
|
74
|
+
# and so on
|
75
|
+
#
|
76
|
+
def occurrences_by(args = {})
|
77
|
+
raise("occurrences_by: arguments must be a Hash") unless args.is_a?(Hash)
|
78
|
+
default_hash = {:type => :any, :value => :any, :scope => :any, :datatype => :any}
|
79
|
+
args = default_hash.merge(args)
|
80
|
+
#filter for type
|
81
|
+
_occurrences = args[:type] == :any ? occurrences : occurrences(args[:type])
|
82
|
+
_occurrences = self.filter_by(_occurrences,args)
|
83
|
+
#filter for datatype
|
84
|
+
_occurrences = _occurrences.select{|o| o.datatype == args[:datatype]} unless args[:datatype] == :any
|
85
|
+
return _occurrences.to_a
|
86
|
+
end
|
87
|
+
|
88
|
+
protected
|
89
|
+
def filter_by(_characteristics,args)
|
90
|
+
#filter for value
|
91
|
+
unless args[:value] == :any
|
92
|
+
_characteristics = args[:value].is_a?(Array) ? _characteristics.select{|o| args[:value].any?{|v| o.value == v}} : _characteristics.select{|o| o.value == args[:value]}
|
93
|
+
end
|
94
|
+
#filter for scope
|
95
|
+
case args[:scope]
|
96
|
+
when :any
|
97
|
+
when :ucs, []
|
98
|
+
_characteristics = _characteristics.select{|o| o.scope.empty?}
|
99
|
+
else
|
100
|
+
_scope = topic_map.get(args[:scope])
|
101
|
+
_characteristics = _scope.is_a?(Array) ? _characteristics.select{|o| _scope.any?{|theme| o.scope.include?(theme)}} : _characteristics.select{|o| o.scope.include?(_scope)}
|
13
102
|
end
|
103
|
+
_characteristics
|
14
104
|
end
|
105
|
+
|
106
|
+
# Returns the Occurrences and Names of this Topic which have the specified type as
|
107
|
+
# Occurrence/Name type. Additionally, scope may constrain the the selection.
|
108
|
+
#
|
109
|
+
# If scope is set to :ucs, Occurrences/Names which exist in the unconstrained scope
|
110
|
+
# are selected. If scope is set to :any (default), scope does not constrain
|
111
|
+
# the Occurrence/Names-Array. Else, only the Occurrences/Names which exist in the given scope
|
112
|
+
# are selected.
|
113
|
+
#
|
114
|
+
# Returns an empty Array if no Occurrences or Names match or if the Occurrence/Name type or
|
115
|
+
# scope does not exist.
|
116
|
+
#
|
117
|
+
# :call-seq:
|
118
|
+
# characteristics_by -> Array of Occurrences and Names
|
119
|
+
#
|
120
|
+
# def characteristics_by(args = {})
|
121
|
+
# raise("characteristics_by: arguments must be a Hash") unless args.is_a?(Hash)
|
122
|
+
# default_hash = {:type => :any, :value => :any, :scope => :any, :datatype => :any}
|
123
|
+
# args = default_hash.merge(args)
|
124
|
+
# _names = names_by(args) if args[:datatype].include(:any) || args[:datatype] == RTM::PSI[:String] || args[:datatype] == topic_map.create_locator(RTM::PSI[:String])
|
125
|
+
# _occurrences = occurrences_by(args)
|
126
|
+
#
|
127
|
+
# end
|
128
|
+
|
15
129
|
end
|
@@ -1,15 +1,150 @@
|
|
1
|
-
|
2
|
-
|
3
|
-
|
4
|
-
|
5
|
-
|
6
|
-
|
7
|
-
|
8
|
-
|
1
|
+
# Copyright: Copyright 2009 Topic Maps Lab, University of Leipzig.
|
2
|
+
# License: Apache License, Version 2.0
|
3
|
+
|
4
|
+
module RTM::Sugar::Topic
|
5
|
+
module Counterparts
|
6
|
+
|
7
|
+
# Returns all Roles belonging to Associations in which this Topic
|
8
|
+
# is a player and for which this Topic is not the player.
|
9
|
+
#
|
10
|
+
# A filter-hash may be used to filter for the the type
|
11
|
+
# of the Role this Topic playes
|
12
|
+
# (:rtype), for the Association type (:atype) and/or
|
13
|
+
# for the type of the returned Roles (:otype). The
|
14
|
+
# identifier may be a topic reference.
|
15
|
+
#
|
16
|
+
# The result may be empty.
|
17
|
+
#
|
18
|
+
# :call-seq:
|
19
|
+
# counterparts -> Array of Roles
|
20
|
+
# counterparts({:rtype => identifier}) -> Array of Roles
|
21
|
+
# counterparts({:atype => identifier}) -> Array of Roles
|
22
|
+
# counterparts({:otype => identifier}) -> Array of Roles
|
23
|
+
# counterparts({:rtype => identifier, :atype => identifier}) -> Array of Roles
|
24
|
+
# counterparts({:rtype => identifier, :atype => identifier, :otype => identifier}) -> Array of Roles
|
25
|
+
#
|
26
|
+
def counterparts(filter={})
|
27
|
+
roles.select{|r| filter[:rtype] ? r.type == self.topic_map.get(filter[:rtype]) : true}.
|
28
|
+
select{|r| filter[:atype] ? r.parent.type == self.topic_map.get(filter[:atype]) : true}.
|
29
|
+
inject([]){|all,r| all+=r.counterparts(filter)}
|
30
|
+
end
|
31
|
+
|
32
|
+
# Returns all Topics that are players of Roles belonging to Associations
|
33
|
+
# in which this Topic is another player. The resulting Array does
|
34
|
+
# not contain duplicates.
|
35
|
+
#
|
36
|
+
# A filter-hash may be used to filter for the the type
|
37
|
+
# of the Role this Topic playes
|
38
|
+
# (:rtype), for the Association type (:atype) and/or
|
39
|
+
# for the type of the Roles the returned Topics play (:otype). The
|
40
|
+
# identifier may be a topic reference.
|
41
|
+
#
|
42
|
+
# The result may be empty.
|
43
|
+
#
|
44
|
+
# :call-seq:
|
45
|
+
# counterplayers -> Array of Topics
|
46
|
+
# counterplayers(:rtype => identifier) -> Array of Topics
|
47
|
+
# counterplayers(:atype => identifier) -> Array of Topics
|
48
|
+
# counterplayers(:otype => identifier) -> Array of Topics
|
49
|
+
# counterplayers(:rtype => identifier1, :atype => identifier2) -> Array of Topics
|
50
|
+
# counterplayers(:rtype => identifier1, :atype => identifier2, :otype => identifier3) -> Array of Topics
|
51
|
+
#
|
52
|
+
def counterplayers(filter={})
|
53
|
+
topic_map.cached self, :counterplayers, filter do
|
54
|
+
counterparts(filter).map{|r| r.player}.uniq
|
55
|
+
end
|
56
|
+
end
|
57
|
+
|
58
|
+
# Returns all players (Topics) which share a counterplayer with this Topic (player),
|
59
|
+
# If type is given, it may constrain the type of the Role this Topic should play
|
60
|
+
# (and therefore the type of the Roles the peers play)
|
61
|
+
# or the type of the Association this Topic plays a Role in
|
62
|
+
# (and therefore the type of the Associations the peers play an Role in).
|
63
|
+
#
|
64
|
+
# Type may be a topic reference.
|
65
|
+
#
|
66
|
+
# The result may be empty.
|
67
|
+
#
|
68
|
+
# :call-seq:
|
69
|
+
# peers -> Array of Topics
|
70
|
+
# peers(type) -> Array of Topics
|
71
|
+
#
|
72
|
+
def peers(type=:any)
|
73
|
+
_peers = []
|
74
|
+
if type == :any
|
75
|
+
self.roles.each do |r|
|
76
|
+
_peers = _peers + r.peers(:arity => :loose, :atype => :loose, :otype => :loose, :rtype => :loose)
|
77
|
+
end
|
78
|
+
else
|
79
|
+
type = topic_map.get(type)
|
80
|
+
if type
|
81
|
+
if self.roles.map{|r| r.type}.include?(type) #-> rtype
|
82
|
+
self.roles(type).each do |r|
|
83
|
+
_peers = _peers + r.peers(:arity => :loose, :atype => :loose, :otype => :loose, :rtype => :strict)
|
84
|
+
end
|
85
|
+
elsif self.roles.map{|r| r.parent.type}.include?(type) #->atype
|
86
|
+
self.roles.select{|r| r.parent.type == type}.each do |r|
|
87
|
+
_peers = _peers + r.peers(:arity => :loose, :atype => :strict, :otype => :loose, :rtype => :strict)
|
88
|
+
end
|
89
|
+
elsif self.roles.map{|r| r.counterparts}.flatten.map{|r| r.type}.include?(type) #-> otype
|
90
|
+
# nothing can happen so far
|
91
|
+
else
|
92
|
+
return []
|
93
|
+
end
|
94
|
+
else
|
95
|
+
return []
|
96
|
+
end
|
9
97
|
end
|
10
|
-
|
11
|
-
|
98
|
+
return _peers.map{|r| r.player}
|
99
|
+
end
|
100
|
+
|
101
|
+
# Returns all Associations in which this Topic
|
102
|
+
# is a player.
|
103
|
+
#
|
104
|
+
# A filter-hash may be used to filter
|
105
|
+
# for the type of the Role this Topic plays (:rtype),
|
106
|
+
# for the Association type (:atype),
|
107
|
+
# for the type of another role (:otype) as well as
|
108
|
+
# for the player of this other role (:oplayer).
|
109
|
+
# Each value of this filter-hash may be a topic reference.
|
110
|
+
#
|
111
|
+
# The result may be empty.
|
112
|
+
#
|
113
|
+
# :call-seq:
|
114
|
+
# associations_played -> Array of Associations
|
115
|
+
# associations_played({:rtype => identifier}) -> Array of Associations
|
116
|
+
# associations_played({:atype => identifier}) -> Array of Associations
|
117
|
+
# associations_played({:otype => identifier}) -> Array of Associations
|
118
|
+
# associations_played({:otype => identifier, :oplayer => identifier}) -> Array of Associations
|
119
|
+
# associations_played({:rtype => identifier, :atype => identifier}) -> Array of Associations
|
120
|
+
# associations_played({:rtype => identifier, :atype => identifier, :otype => identifier}) -> Array of Associations
|
121
|
+
# associations_played({:rtype => identifier, :atype => identifier, :otype => identifier, :oplayer => identifier}) -> Array of Associations
|
122
|
+
#
|
123
|
+
def associations_played(filter = {})
|
124
|
+
topic_map.cached self, :associations_played, filter do
|
125
|
+
raise("associations_played(filter): filter must be a Hash") unless filter.is_a?(Hash)
|
126
|
+
default_hash = {:rtype => :any, :atype => :any, :otype => :any, :oplayer => :any}
|
127
|
+
filter = default_hash.merge(filter)
|
128
|
+
|
129
|
+
# get all roles played
|
130
|
+
roles = self.roles_played(filter[:rtype], filter[:atype])
|
131
|
+
filter.delete(:rtype)
|
132
|
+
filter.delete(:atype)
|
133
|
+
|
134
|
+
#filter for the other roles types and players if there are other roles
|
135
|
+
roles = roles.reject do |role|
|
136
|
+
if role.parent.roles.size == 1 #association size
|
137
|
+
if (filter[:otype] != :any) || filter[:player] != :any
|
138
|
+
end
|
139
|
+
else
|
140
|
+
role.counterparts(filter).empty?
|
141
|
+
end
|
142
|
+
end
|
143
|
+
|
144
|
+
# return parent associations
|
145
|
+
roles.map{|role| role.parent}.uniq
|
12
146
|
end
|
13
147
|
end
|
148
|
+
|
14
149
|
end
|
15
150
|
end
|
@@ -1,52 +1,162 @@
|
|
1
|
+
# Copyright: Copyright 2009 Topic Maps Lab, University of Leipzig.
|
2
|
+
# License: Apache License, Version 2.0
|
3
|
+
|
1
4
|
module RTM::Sugar
|
2
5
|
module Topic
|
6
|
+
# This module implements methods for Hash-like access in Topics.
|
3
7
|
module HashAccess
|
4
|
-
|
5
|
-
|
6
|
-
|
7
|
-
|
8
|
+
|
9
|
+
# Returns an Array of Names or Occurrences of
|
10
|
+
# this Topic depending on the argument given.
|
11
|
+
#
|
12
|
+
# If argument is a Topic, an Array of Occurrences of this Topic which
|
13
|
+
# have the specified type is returned.
|
14
|
+
#
|
15
|
+
# Argument may be a String. Then the structure should resemble "-type @scope"
|
16
|
+
# or "type @scope".
|
17
|
+
#
|
18
|
+
# If argument starts with a "-", an Array of Names of this
|
19
|
+
# Topic, which have the specified type (trailing the "-"),
|
20
|
+
# is returned.
|
21
|
+
#
|
22
|
+
# If argument equals "-", Names that have the standard name type
|
23
|
+
# are returned.
|
24
|
+
#
|
25
|
+
# If argument starts with a "*", both Names and Occurrences, which have the
|
26
|
+
# specified type (trailing the "*") are returned as Array.
|
27
|
+
#
|
28
|
+
# If argument equals "*", all Names and Occurrences of this Topic are
|
29
|
+
# returned. In this case this method equals the characteristics()-method.
|
30
|
+
#
|
31
|
+
# Else, if argument is a String, an Array of Occurrences
|
32
|
+
# of this Topic, which have the specified type,
|
33
|
+
# is returned.
|
34
|
+
#
|
35
|
+
# The argument may include an "@" after the type.
|
36
|
+
# The String trailing the @ defines the
|
37
|
+
# scope the selected Names and Occurrences should live in. Themes in the
|
38
|
+
# scope may be c.
|
39
|
+
#
|
40
|
+
# Examples:
|
41
|
+
# topic[occtype_topic]
|
42
|
+
# topic["-"]
|
43
|
+
# topic["*"]
|
44
|
+
# topic["-nametype"]
|
45
|
+
# topic["-nametype @scope]
|
46
|
+
# topic["occtype @scope1, scope2"]
|
47
|
+
# topic["*type"]
|
48
|
+
# topic["*type @scope"]
|
49
|
+
#
|
50
|
+
# :call-seq:
|
51
|
+
# [argument=Topic] -> Array of Occurrences
|
52
|
+
# [argument=String] -> Array of Names and/or Occurrences
|
53
|
+
#
|
54
|
+
def [](identifier = :any)
|
55
|
+
# return occurrences by type if topic is given
|
56
|
+
return [] unless identifier
|
57
|
+
return occurrences(identifier).to_a if (identifier.is_a?(RTM::Topic) || identifier == :any)
|
58
|
+
prefix, type_reference, scope_reference = resolve_characteristic(identifier)
|
59
|
+
if prefix == :name
|
8
60
|
type_reference = RTM::PSI[:name_type] if type_reference == :any
|
9
|
-
|
10
|
-
|
61
|
+
ret = names(type_reference).to_a
|
62
|
+
elsif prefix == :occurrence
|
11
63
|
raise "No occurrence type given" if type_reference == :any
|
12
|
-
|
64
|
+
ret = occurrences(type_reference).to_a
|
65
|
+
elsif prefix == :both
|
66
|
+
ret = names(type_reference).to_a + occurrences(type_reference).to_a # type_reference == :any or not :any
|
67
|
+
else
|
68
|
+
|
69
|
+
end
|
70
|
+
# we now have a list of names or occurrences, now we have to select for scope
|
71
|
+
return ret if scope_reference == :any
|
72
|
+
if scope_reference == :ucs
|
73
|
+
ret.select{|i| i.scope.size == 0}
|
74
|
+
else
|
75
|
+
ret = ret.select{|i| scope_reference.all?{|sr| i.scope.include? getParent.get(sr)}}
|
13
76
|
end
|
77
|
+
ret
|
14
78
|
end
|
15
79
|
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
80
|
+
# Creates a Name or Occurrence of this Topic depending on the
|
81
|
+
# argument given and returns this Name/Occurrence.
|
82
|
+
#
|
83
|
+
# Argument may be a String whose structure should resemble "-type @scope"
|
84
|
+
# or "type @scope".
|
85
|
+
#
|
86
|
+
# If argument starts with a "-", a Name that has the specified type
|
87
|
+
# (trailing the "-") is created.
|
88
|
+
#
|
89
|
+
# If argument equals "-", a Name that hase the standard name type
|
90
|
+
# is created.
|
91
|
+
#
|
92
|
+
# Else, an Occurrence that has the specified type is created.
|
93
|
+
#
|
94
|
+
# The argument may include an "@" after the type. The String trailing
|
95
|
+
# the @ defines the optional scope the Name or Occurrence
|
96
|
+
# should live in. Themes in the scope may be comma- and/or space-separated.
|
97
|
+
#
|
98
|
+
# The value should be a String.
|
99
|
+
#
|
100
|
+
# Example:
|
101
|
+
# topic[occtype]= "occvalue"
|
102
|
+
# topic["-"]= "name"
|
103
|
+
# topic["-nametype"]= "name"
|
104
|
+
# topic["-nametype @scope]= "name"
|
105
|
+
# topic["occtype @scope1, scope2"]= "occvalue"
|
106
|
+
#
|
107
|
+
# :call-seq:
|
108
|
+
# [argument]= value
|
109
|
+
#
|
110
|
+
def []=(identifier, value)
|
111
|
+
prefix, type_reference, scope_reference = resolve_characteristic(identifier)
|
112
|
+
if prefix == :name
|
113
|
+
nametype = (type_reference==:any) ? topic_map.get!(RTM::PSI[:name_type]) : type_reference
|
114
|
+
scope_reference = scope_reference==:any ? [] : scope_reference
|
115
|
+
raise("Value is not a String") unless value.is_a?(String)
|
116
|
+
ret = create_name(nametype, value, scope_reference)
|
117
|
+
elsif prefix == :occurrence
|
24
118
|
raise "No occurrence type given" if type_reference == :any
|
25
|
-
|
26
|
-
|
119
|
+
ret = create_occurrence(type_reference, value)
|
120
|
+
else
|
121
|
+
return nil
|
27
122
|
end
|
123
|
+
# return object without scope if any or ucs
|
124
|
+
return ret if [:any, :ucs].include? scope_reference
|
125
|
+
# set scope
|
126
|
+
ret.add_scope(scope_reference)
|
127
|
+
ret
|
28
128
|
end
|
29
|
-
|
129
|
+
|
30
130
|
private
|
31
|
-
|
32
|
-
|
33
|
-
|
131
|
+
|
132
|
+
def resolve_characteristic(identifier)
|
133
|
+
# spaces(-|*)?spaces(anything)
|
134
|
+
prefix = :occurrence
|
135
|
+
identifier =~ /^\s*(-|\*)?\s*(.+)?$/ # - or * and then everything else
|
136
|
+
if $1
|
137
|
+
prefix = ($1 == "-") ? :name : :both
|
138
|
+
end
|
34
139
|
type, scope = resolve_type_and_scope($2)
|
35
|
-
[
|
140
|
+
[prefix, type, scope]
|
36
141
|
end
|
37
|
-
|
142
|
+
|
38
143
|
def resolve_type_and_scope(ref)
|
39
144
|
return [:any, :any] unless ref
|
40
|
-
|
41
|
-
type, scope = ref.split('@', -1)
|
42
|
-
if type.blank?
|
145
|
+
if ref[0] == ?@
|
43
146
|
type = :any
|
147
|
+
scope = ref[1..-1] #cut "@"
|
44
148
|
else
|
45
|
-
type.
|
149
|
+
type, scope = ref.split(' @', -1) # -1 -> trailing null fields are not suppressed
|
150
|
+
if (type == nil) || (type.length == 0)
|
151
|
+
type = :any
|
152
|
+
else
|
153
|
+
type.strip! #\s removed
|
154
|
+
end
|
46
155
|
end
|
156
|
+
|
47
157
|
if scope
|
48
|
-
scope = scope.strip.split(/\s+/)
|
49
|
-
scope = :ucs if scope.
|
158
|
+
scope = scope.strip.split(/\s*,?\s+/) #divided at \s,\s
|
159
|
+
scope = :ucs if (scope == nil) || (scope.length == 0)
|
50
160
|
else
|
51
161
|
scope = :any
|
52
162
|
end
|
@@ -54,4 +164,4 @@ module RTM::Sugar
|
|
54
164
|
end
|
55
165
|
end
|
56
166
|
end
|
57
|
-
end
|
167
|
+
end
|