nlg 0.0.1

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,5 @@
1
+ *.gem
2
+ .bundle
3
+ Gemfile.lock
4
+ pkg/*
5
+ doc/*
data/Gemfile ADDED
@@ -0,0 +1,4 @@
1
+ source "http://rubygems.org"
2
+
3
+ # Specify your gem's dependencies in nlg.gemspec
4
+ gemspec
data/README ADDED
File without changes
@@ -0,0 +1,10 @@
1
+ require "bundler/gem_tasks"
2
+ require 'rake/testtask'
3
+
4
+ task :default => :test
5
+ Rake::TestTask.new(:test) do |test|
6
+ test.libs << 'lib' <<'test'
7
+ test.pattern = 'test/*_test.rb'
8
+ test.verbose = true
9
+ end
10
+ # test.pattern = 'test/*_test.rb'
@@ -0,0 +1,12 @@
1
+ require "active_support"
2
+ require "verbs"
3
+ require "nlg/sentence"
4
+ require "nlg/nlg_exception"
5
+ require "nlg/version"
6
+ require "nlg/paragraph"
7
+ require "nlg/sentence"
8
+ require "nlg/sentence_object"
9
+
10
+ module Nlg
11
+ # Your code goes here...
12
+ end
@@ -0,0 +1,2 @@
1
+ class NlgException < Exception
2
+ end
@@ -0,0 +1,125 @@
1
+ module Nlg
2
+ class Paragraph
3
+
4
+ attr_accessor :defaults, :dataset, :sentences
5
+ # The parameters, dataset and defaults are both hashes.
6
+ # For example:
7
+ #
8
+ # defaults = { "tense" => "present",
9
+ # "verb" => "have",
10
+ # "pronoun" => "it",
11
+ # "voice" => "active",
12
+ # "aspect" => "habitual",
13
+ # "preposition" => "of" }
14
+ #
15
+ # dataset = {"subject"=>"Pune",
16
+ # "objects"=>
17
+ # { "population"=>
18
+ # {"value"=>"57841284790",
19
+ # "specifications"=>{}},
20
+ # "rainfall"=>
21
+ # {"value"=>"198",
22
+ # "specifications"=>{"complement"=>"mm"}},
23
+ # "high temperature"=>
24
+ # {"value"=>"45",
25
+ # "specifications"=>{"complement"=>"°C"},
26
+ # "conjugated_with"=>["low temperature"]},
27
+ # "low temperature"=>
28
+ # {"value"=>"20",
29
+ # "specifications"=>{"complement"=>"°C"},
30
+ # "conjugated_with"=>["high temperature", "low temperature", "rainfall"]},
31
+ # "forts"=>
32
+ # {"value"=>["sinhgad", "lohgad"],
33
+ # "specifications"=>{"preposition"=>"named"},
34
+ # "conjugated_with"=>["high temperature", "low temperature", "rainfall"]}
35
+ # }
36
+ # }
37
+ #
38
+ # method to set defaults, build_conjugations and initialize other attributes
39
+ def initialize(dataset, defaults)
40
+ @subject = dataset['subject']
41
+ @objects = {}
42
+ @conjugations = {}
43
+ @defaults = defaults
44
+ @sentences = []
45
+
46
+ # Iterating through all the objects and building conjugations.
47
+ dataset['objects'].each do |object_type, object_details|
48
+ # A check to allow objects to be created with "conjugated" => false only if not already
49
+ # present. build_conjugations method called which recursively builds the conjugations.
50
+ unless @objects.has_key?(object_type)
51
+ sentence_object = SentenceObject.new(object_type, object_details, "conjugated" => false)
52
+ @objects[object_type] = sentence_object
53
+ build_conjugations(object_type, dataset['objects'])
54
+ end
55
+ end
56
+
57
+ end
58
+
59
+ def build
60
+ puts @conjugations.inspect, @objects.inspect
61
+ # Paragraph generation by generating individual sentences.
62
+ @objects.each do |object_type, sentence_object|
63
+ sentence = Sentence.new(:subject => @subject, :specifications => @defaults.merge(sentence_object.specifications))
64
+ @sentences << sentence.build(object_type, sentence_object)
65
+ end
66
+ end
67
+
68
+ # Method called internally in initialize to build conjugations among sentences of a paragraph.
69
+ # The example dataset will give the conjugations,
70
+ #
71
+ # @conjugations ={"population"=>[], "forts"=>["low temperature", "rainfall", "high temperature"]}
72
+ def build_conjugations(object_type, objects, parent_object = nil)
73
+ object_details = objects[object_type]
74
+
75
+ # Condition for setting the parent_object to be passed recursively
76
+ parent_object = object_type unless parent_object
77
+
78
+ # Creating the @conjugations[parent_object] array recursively to finally
79
+ # build the conjugations.
80
+ conjugated_with = object_details['conjugated_with']
81
+
82
+ unless conjugated_with.nil? or conjugated_with.empty?
83
+ conjugated_with.each do |conjugated_object|
84
+ if objects.has_key?(conjugated_object)
85
+
86
+ # Creating object with "conjugated" => true if its present in "conjugated_with" array.
87
+ unless @objects.has_key?(conjugated_object)
88
+ sentence_object = SentenceObject.new(conjugated_object, objects[conjugated_object], "conjugated" => true)
89
+ @objects[conjugated_object] = sentence_object
90
+ end
91
+
92
+ # Creating array if does not already exist.
93
+ @conjugations[parent_object] ||= []
94
+
95
+ # Checking if currently iterating object included in the array already/is the parent_object itself.
96
+ unless @conjugations[parent_object].include?(conjugated_object) or conjugated_object == parent_object
97
+
98
+ # If an already parsed object with "conjugated" = false comes as a conjugation
99
+ # to the object being parsed.
100
+ if @objects[conjugated_object].conjugated == false
101
+ @objects[conjugated_object].conjugated = true
102
+ @conjugations[parent_object] = @conjugations[parent_object].concat(@conjugations[conjugated_object]).uniq
103
+ @conjugations.delete(conjugated_object)
104
+ end
105
+
106
+ # Appending to the conjugations array for the parent_object.
107
+ @conjugations[parent_object] << conjugated_object
108
+
109
+ # recursive call for building conjugations for a parent_object
110
+ build_conjugations(conjugated_object, objects, parent_object)
111
+ end
112
+ else
113
+ raise NlgException.new "No object named #{conjugation_object}"
114
+ end
115
+ end
116
+ else
117
+
118
+ # adding independent sentences which have no conjugations
119
+ @conjugations[object_type] = [] if @objects[object_type].conjugated == false
120
+ end
121
+
122
+ end
123
+ end
124
+
125
+ end
@@ -0,0 +1,52 @@
1
+ module Nlg
2
+ class Sentence
3
+
4
+ attr_accessor :verb, :tense, :pronoun, :voice, :subject, :value, :object
5
+ attr_accessor :complement, :coordination_phrase, :preposition, :aspect
6
+
7
+ def initialize(args = {})
8
+ specifications = args[:specifications]
9
+ @verb = specifications["verb"] || (raise NlgException.new "Verb is nil")
10
+ @tense = specifications["tense"] || (raise NlgException.new "tense is nil")
11
+ @pronoun = specifications["pronoun"] || (raise NlgException.new "pronoun is nil")
12
+ @complement = specifications["complement"]
13
+ @coordination_phrase = specifications["coordination_phrase"]
14
+ @voice = specifications["voice"]
15
+ @aspect = specifications["aspect"] || (raise NlgException.new "aspect is nil")
16
+ @preposition = specifications["preposition"]
17
+ @subject = args[:subject] || true
18
+ end
19
+
20
+ #method to build a sentence. Returns the formed sentece to build_paragraph
21
+ def build(object_type, object_details)
22
+ self.value = object_details.value
23
+ self.value = value.join(',') if value.is_a?(Array)
24
+ self.object = object_type
25
+ formed_sentence = self.form
26
+ return formed_sentence
27
+ end
28
+
29
+ #method to form the sentence using the given specifications
30
+ def form
31
+ set_tense
32
+ predicate = set_predicate
33
+ formed_sentence = "#{verb} #{predicate}".verb.conjugate :subject => subject, :tense => tense.to_sym, :aspect => aspect.to_sym
34
+ return "#{formed_sentence} #{complement}"
35
+ end
36
+
37
+ def set_tense
38
+ if tense == "past" and aspect == "habitual"
39
+ self.aspect = "perfective"
40
+ end
41
+ end
42
+
43
+ def set_predicate
44
+ predicate = "#{preposition} #{value}"
45
+ if verb == "have"
46
+ predicate = "#{object} #{preposition} #{value}"
47
+ end
48
+ return predicate
49
+ end
50
+
51
+ end
52
+ end
@@ -0,0 +1,15 @@
1
+ module Nlg
2
+ class SentenceObject
3
+ attr_accessor :specifications, :value, :object_type, :conjugated
4
+
5
+ def initialize(object_type, object_details, options={})
6
+ puts object_details
7
+ @specifications = object_details['specifications'] if object_details['specifications']
8
+ @value = object_details['value']
9
+ @object_type = object_type
10
+ @conjugated = options["conjugated"]
11
+ end
12
+
13
+ end
14
+ end
15
+
@@ -0,0 +1,3 @@
1
+ module Nlg
2
+ VERSION = "0.0.1"
3
+ end
@@ -0,0 +1,25 @@
1
+ # -*- encoding: utf-8 -*-
2
+ $:.push File.expand_path("../lib", __FILE__)
3
+ require "nlg/version"
4
+
5
+ Gem::Specification.new do |s|
6
+ s.name = "nlg"
7
+ s.version = Nlg::VERSION
8
+ s.authors = ["Sricharan Sunder", "Jiren Patel", "Gautam Rege"]
9
+ s.email = ["sricharan@joshsoftware.com", "jiren@joshsoftware.com", "gautam@joshsoftware.com"]
10
+ s.homepage = "http://github.com/joshsoftware/nlg"
11
+ s.summary = %q{Natural Language Generation in Ruby}
12
+ s.description = %q{Build articles and paragraphs from structured data. Instead of a standard tempate, we can use this to build articles that are grammatically correct and creative.}
13
+
14
+ s.rubyforge_project = "nlg"
15
+
16
+ s.files = `git ls-files`.split("\n")
17
+ s.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
18
+ s.executables = `git ls-files -- bin/*`.split("\n").map{ |f| File.basename(f) }
19
+ s.require_paths = ["lib"]
20
+ s.add_dependency "verbs"
21
+ s.add_dependency "active_support"
22
+ # specify any dependencies here; for example:
23
+ # s.add_development_dependency "rspec"
24
+ # s.add_runtime_dependency "rest-client"
25
+ end
@@ -0,0 +1,84 @@
1
+ { "defaults":
2
+ { "tense": "present",
3
+ "verb": "be",
4
+ "pronoun": "he",
5
+ "voice": "active",
6
+ "aspect": "habitual"
7
+ },
8
+
9
+ "subjects":
10
+ {
11
+ "subject": "Sricharan",
12
+ "objects": [
13
+ { "object" : "location",
14
+ "value": "aundh",
15
+ "specifications":
16
+ {
17
+ "verb": "live",
18
+ "preposition": "in",
19
+ "tense": "past",
20
+ "coordinated": true,
21
+ "coordination_phrase": "and"}
22
+ },
23
+
24
+
25
+ { "object": "age",
26
+ "value": "19",
27
+ "specifications":
28
+ {"complement": "years old"
29
+ }
30
+ },
31
+
32
+
33
+ { "object": "workplace",
34
+ "value": "Josh Software",
35
+ "specifications":
36
+ {
37
+ "verb": "work",
38
+ "preposition": "in",
39
+ "coordinated": true,
40
+ "coordination_phrase": "and"}
41
+ },
42
+
43
+
44
+ { "object": "interest",
45
+ "value": ["music", "football", "movies"],
46
+ "specifications":
47
+ {
48
+ "verb": "like",
49
+ "coordinated": true,
50
+ "coordination_phrase": "and" }
51
+ },
52
+
53
+
54
+ { "object": "achievement",
55
+ "value": "xyz",
56
+ "specifications":
57
+ {
58
+ "verb": "achieve",
59
+ "aspect": "perfect",
60
+ "coordinated": true,
61
+ "coordination_phrase": "and"}
62
+ },
63
+
64
+
65
+ { "object": "height",
66
+ "value": "185",
67
+ "specifications":
68
+ {
69
+ "complement": "cm tall"}
70
+ },
71
+
72
+
73
+ { "object": "weight",
74
+ "value": "70",
75
+ "specifications":
76
+ {
77
+ "verb": "weigh",
78
+ "complement": "kg"}
79
+ }
80
+ ]
81
+ }
82
+
83
+ }
84
+
@@ -0,0 +1,65 @@
1
+ { "defaults":
2
+ { "tense": "present",
3
+ "verb": "have",
4
+ "pronoun": "it",
5
+ "voice": "active",
6
+ "aspect": "habitual",
7
+ "preposition": "of"
8
+ },
9
+
10
+ "subjects":
11
+ {
12
+ "subject": "Pune",
13
+ "objects": {
14
+ "population":{
15
+ "value": "57841284790",
16
+ "specifications":
17
+ {
18
+
19
+ }
20
+ },
21
+
22
+
23
+ "rainfall": {
24
+ "value": "198",
25
+ "specifications":
26
+ {
27
+ "complement": "mm"}
28
+
29
+ },
30
+
31
+
32
+ "high temperature": {
33
+ "value": "45",
34
+ "specifications": {
35
+ "complement": "°C"
36
+ },
37
+ "conjugated_with": ["low temperature"]
38
+ },
39
+
40
+
41
+ "low temperature": {
42
+ "value": "20",
43
+ "specifications":
44
+ {
45
+ "complement": "°C" },
46
+ "conjugated_with": ["high temperature", "low temperature", "rainfall"]
47
+ },
48
+
49
+
50
+
51
+ "forts": {
52
+ "value": ["sinhgad", "lohgad"],
53
+ "specifications":
54
+ {
55
+ "preposition": "named"
56
+ },
57
+ "conjugated_with": ["high temperature", "low temperature", "rainfall"]
58
+
59
+ }
60
+ }
61
+ }
62
+
63
+
64
+ }
65
+
@@ -0,0 +1,57 @@
1
+ { "defaults":
2
+ { "tense": "present",
3
+ "verb": "be",
4
+ "pronoun": "it",
5
+ "voice": "active",
6
+ "aspect": "habitual"
7
+ },
8
+
9
+ "subjects":
10
+ {
11
+ "subject": "ABCD",
12
+ "objects": [
13
+ { "object" : "type",
14
+ "value": "bottle",
15
+ "specifications":
16
+ {"preposition": "a"
17
+ }
18
+ },
19
+
20
+
21
+ { "object": "height",
22
+ "value": "123",
23
+ "specifications":
24
+ {
25
+ "complement": "mm high."}
26
+ },
27
+
28
+
29
+ { "object": "dimension",
30
+ "value": "12*2*3",
31
+ "specifications":
32
+ {"verb": "have"
33
+ }
34
+ },
35
+
36
+
37
+ { "object": "weight",
38
+ "value": "20",
39
+ "specifications":
40
+ {"verb": "weigh",
41
+ "complement": "gm" }
42
+ },
43
+
44
+
45
+
46
+ { "object": "cost",
47
+ "value": "123",
48
+ "specifications":
49
+ {"verb": "cost",
50
+ "complement": "rupees."
51
+ }
52
+ }
53
+ ]
54
+ }
55
+
56
+ }
57
+
@@ -0,0 +1,31 @@
1
+ require "test_helper"
2
+
3
+ class SentenceTest < ActiveSupport::TestCase
4
+
5
+ def setup
6
+ dataset_json = File.read("test/sentence_test_json.txt")
7
+ dataset = JSON.parse(dataset_json)
8
+ @defaults = dataset['defaults']
9
+ @subject = dataset['subjects']['subject']
10
+ @objects = dataset['subjects']['objects']
11
+ @objects.each do |object_type, object_details|
12
+ @sentence_hash= {object_type => object_details}
13
+ end
14
+ end
15
+
16
+ def teardown
17
+
18
+ end
19
+
20
+ test "should init sentence" do
21
+ sentence = Nlg::Sentence.new(:subject => @subject, :specifications => @defaults.merge(@sentence_hash[@sentence_hash.keys.first]["specifications"]))
22
+ assert_equal @subject, sentence.subject
23
+ end
24
+
25
+ test "" do
26
+ @subject = nil
27
+ assert_raise NlgException
28
+ Sentence.new()
29
+
30
+ end
31
+ end
@@ -0,0 +1,28 @@
1
+ { "defaults":
2
+ { "tense": "present",
3
+ "verb": "have",
4
+ "pronoun": "it",
5
+ "voice": "active",
6
+ "aspect": "habitual",
7
+ "preposition": "of"
8
+ },
9
+
10
+ "subjects":
11
+ {
12
+ "subject": "Pune",
13
+ "objects": {
14
+ "population":{
15
+ "value": "57841284790",
16
+ "specifications":
17
+ {
18
+
19
+ }
20
+ }
21
+
22
+
23
+ }
24
+ }
25
+
26
+
27
+ }
28
+
@@ -0,0 +1,13 @@
1
+ $LOAD_PATH.unshift(File.dirname(__FILE__))
2
+ $LOAD_PATH.unshift(File.join(File.dirname(__FILE__), '..', 'lib'))
3
+ require "nlg"
4
+
5
+ dataset_json = File.read("json_place.txt")
6
+ dataset = JSON.parse(dataset_json)
7
+ paragraph = Nlg::Paragraph.new(dataset["subjects"], dataset["defaults"])
8
+ paragraph.build
9
+ paragraph.sentences.each do |sentence|
10
+ puts sentence
11
+ end
12
+
13
+
@@ -0,0 +1,7 @@
1
+ require "test/unit"
2
+ require 'active_support/test_case'
3
+ $LOAD_PATH.unshift(File.dirname(__FILE__))
4
+ $LOAD_PATH.unshift(File.join(File.dirname(__FILE__), '..', 'lib'))
5
+ require "nlg"
6
+
7
+
metadata ADDED
@@ -0,0 +1,97 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: nlg
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.1
5
+ prerelease:
6
+ platform: ruby
7
+ authors:
8
+ - Sricharan Sunder
9
+ - Jiren Patel
10
+ - Gautam Rege
11
+ autorequire:
12
+ bindir: bin
13
+ cert_chain: []
14
+ date: 2012-01-11 00:00:00.000000000Z
15
+ dependencies:
16
+ - !ruby/object:Gem::Dependency
17
+ name: verbs
18
+ requirement: &10469010 !ruby/object:Gem::Requirement
19
+ none: false
20
+ requirements:
21
+ - - ! '>='
22
+ - !ruby/object:Gem::Version
23
+ version: '0'
24
+ type: :runtime
25
+ prerelease: false
26
+ version_requirements: *10469010
27
+ - !ruby/object:Gem::Dependency
28
+ name: active_support
29
+ requirement: &10468800 !ruby/object:Gem::Requirement
30
+ none: false
31
+ requirements:
32
+ - - ! '>='
33
+ - !ruby/object:Gem::Version
34
+ version: '0'
35
+ type: :runtime
36
+ prerelease: false
37
+ version_requirements: *10468800
38
+ description: Build articles and paragraphs from structured data. Instead of a standard
39
+ tempate, we can use this to build articles that are grammatically correct and creative.
40
+ email:
41
+ - sricharan@joshsoftware.com
42
+ - jiren@joshsoftware.com
43
+ - gautam@joshsoftware.com
44
+ executables: []
45
+ extensions: []
46
+ extra_rdoc_files: []
47
+ files:
48
+ - .gitignore
49
+ - Gemfile
50
+ - README
51
+ - Rakefile
52
+ - lib/nlg.rb
53
+ - lib/nlg/nlg_exception.rb
54
+ - lib/nlg/paragraph.rb
55
+ - lib/nlg/sentence.rb
56
+ - lib/nlg/sentence_object.rb
57
+ - lib/nlg/version.rb
58
+ - nlg.gemspec
59
+ - test/json.txt
60
+ - test/json_place.txt
61
+ - test/json_thing.txt
62
+ - test/sentence_test.rb
63
+ - test/sentence_test_json.txt
64
+ - test/test2.rb
65
+ - test/test_helper.rb
66
+ homepage: http://github.com/joshsoftware/nlg
67
+ licenses: []
68
+ post_install_message:
69
+ rdoc_options: []
70
+ require_paths:
71
+ - lib
72
+ required_ruby_version: !ruby/object:Gem::Requirement
73
+ none: false
74
+ requirements:
75
+ - - ! '>='
76
+ - !ruby/object:Gem::Version
77
+ version: '0'
78
+ required_rubygems_version: !ruby/object:Gem::Requirement
79
+ none: false
80
+ requirements:
81
+ - - ! '>='
82
+ - !ruby/object:Gem::Version
83
+ version: '0'
84
+ requirements: []
85
+ rubyforge_project: nlg
86
+ rubygems_version: 1.8.10
87
+ signing_key:
88
+ specification_version: 3
89
+ summary: Natural Language Generation in Ruby
90
+ test_files:
91
+ - test/json.txt
92
+ - test/json_place.txt
93
+ - test/json_thing.txt
94
+ - test/sentence_test.rb
95
+ - test/sentence_test_json.txt
96
+ - test/test2.rb
97
+ - test/test_helper.rb