-
Notifications
You must be signed in to change notification settings - Fork 0
/
name-extractor.js
65 lines (52 loc) · 1.69 KB
/
name-extractor.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
var minors = require('title-case-minors').reduce(function (obj, minor) {
obj[minor] = true
return obj
}, {})
, Extractor = function (input) {
this.tokens = input.trim().split(/\s+/)
this.names = []
},
isCapitalized = function (string) {
return string[0] >= 'A' && string[0] <= 'Z'
},
isTitleMinorCase = function (string) {
// make it possible for a title minor case word to be at the end of a
// sentence (or something similar)
return minors[string.replace(/[^a-z]*$/, '')]
}
Extractor.prototype._findNamesWithMinor = function (startIndex) {
var index = startIndex + 1
// first, step to the capitalized word
while((token = this.tokens[index]) && isTitleMinorCase(token))
index++
// second, add all the words that are capitalized or minors
while((token = this.tokens[index]) && (isCapitalized(token) || isTitleMinorCase(token))) {
this.names.push(this.tokens.slice(startIndex, index + 1).join(' '))
index++
}
}
Extractor.prototype._findNames = function (startIndex) {
var index = startIndex
, token
while((token = this.tokens[index]) && (isCapitalized(token) || isTitleMinorCase(token))) {
this.names.push(this.tokens.slice(startIndex, index + 1).join(' '))
index++
}
index = startIndex - 1
while((token = this.tokens[index]) && minors[token]) {
this._findNamesWithMinor(index)
index--
}
}
Extractor.prototype.extract = function () {
var self = this
this.tokens.forEach(function (token, index) {
if (isCapitalized(token))
self._findNames(index)
})
return this.names
}
module.exports = function (input) {
var extractor = new Extractor(input)
return extractor.extract()
}