Julien Chaumond commited on
Commit
ee12ee4
·
1 Parent(s): 6556bb5

Checkpoint 3

Browse files
Files changed (2) hide show
  1. js-src/Displacy.ts +56 -15
  2. js-src/coref.ts +2 -2
js-src/Displacy.ts CHANGED
@@ -10,14 +10,54 @@ interface Span {
10
  end: number;
11
  }
12
 
 
 
 
 
 
13
  class Displacy {
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
14
 
15
  /**
16
  * Render a text string and its entity spans
17
  *
18
  * *see displacy-ent.js*
 
19
  */
20
  static render(text: string, spans: Span[]): string {
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
21
  let out = {
22
  __content: "",
23
  append(s: string) {
@@ -26,23 +66,24 @@ class Displacy {
26
  };
27
  let offset = 0;
28
 
29
- spans.forEach(({ type, start, end }) => {
30
- const entity = text.slice(start, end);
31
- const fragments = text.slice(offset, start).split('\n');
32
-
33
- fragments.forEach((fragment, i) => {
34
- out.append(fragment);
35
- if (fragments.length > 1 && i !== fragments.length - 1) {
36
- out.append('<br>');
37
- }
38
- });
39
 
40
- // Breaking change from displacy-ent.js:
41
- // We do not filter any entity type out.
42
- out.append(`<mark data-entity=${ type.toLowerCase() }>${ entity }</mark>`);
43
 
44
- offset = end;
45
- });
 
 
 
 
 
 
46
 
47
  out.append(text.slice(offset, text.length));
48
  return out.__content;
 
10
  end: number;
11
  }
12
 
13
+ interface SpanTag {
14
+ span: Span;
15
+ tag: "start" | "end";
16
+ }
17
+
18
  class Displacy {
19
+ static sortSpans(spans: Span[]) {
20
+ spans.sort((a, b) => { /// `a` should come first when the result is < 0
21
+ if (a.start === b.start) {
22
+ return b.end - a.end; /// CAUTION.
23
+ }
24
+ return a.start - b.start;
25
+ });
26
+
27
+ // Check existence of **strict overlapping**
28
+ spans.forEach((s, i) => {
29
+ if (i < spans.length - 1) {
30
+ const sNext = spans[i+1];
31
+ if (s.start < sNext.start && s.end > sNext.start) {
32
+ alert("Spans: strict overlapping");
33
+ }
34
+ }
35
+ });
36
+ }
37
 
38
  /**
39
  * Render a text string and its entity spans
40
  *
41
  * *see displacy-ent.js*
42
+ * see https://github.com/explosion/displacy-ent/issues/2
43
  */
44
  static render(text: string, spans: Span[]): string {
45
+ this.sortSpans(spans);
46
+
47
+ const tags: { [index: number]: SpanTag[] } = {};
48
+ const __addTag = (i: number, s: Span, tag: "start" | "end") => {
49
+ if (Array.isArray(tags[i])) {
50
+ tags[i].push({ span: s, tag: tag });
51
+ } else {
52
+ tags[i] = [{ span: s, tag: tag }];
53
+ }
54
+ };
55
+ for (const s of spans) {
56
+ __addTag(s.start, s, "start");
57
+ __addTag(s.end, s, "end");
58
+ }
59
+ // console.log(JSON.stringify(tags)); // todo remove
60
+
61
  let out = {
62
  __content: "",
63
  append(s: string) {
 
66
  };
67
  let offset = 0;
68
 
69
+ const indexes = Object.keys(tags).map(k => parseInt(k, 10)).sort((a, b) => a - b); /// CAUTION
70
+ for (const i of indexes) {
71
+ const spanTags = tags[i];
72
+ // console.log(i, spanTags); // todo remove
73
+ if (i > offset) {
74
+ out.append(text.slice(offset, i));
75
+ }
 
 
 
76
 
77
+ offset = i;
 
 
78
 
79
+ for (const sT of spanTags) {
80
+ if (sT.tag === "start") {
81
+ out.append(`<mark data-entity="${ sT.span.type.toLowerCase() }">`);
82
+ } else {
83
+ out.append(`</mark>`);
84
+ }
85
+ }
86
+ }
87
 
88
  out.append(text.slice(offset, text.length));
89
  return out.__content;
js-src/coref.ts CHANGED
@@ -63,9 +63,9 @@ class Coref {
63
  }
64
 
65
  render(res: Response) {
66
- const markup = Displacy.render(res.cleanedText, (<any>res).entities);
67
  if (!this.container) { return ; }
68
- console.log(markup);
69
  this.container.innerHTML = `<div class="text">${markup}</div>`;
70
  }
71
  }
 
63
  }
64
 
65
  render(res: Response) {
66
+ const markup = Displacy.render(res.cleanedText, (<any>res).entities); // We will sort the second param in Displacy
67
  if (!this.container) { return ; }
68
+ console.log(markup); // todo remove
69
  this.container.innerHTML = `<div class="text">${markup}</div>`;
70
  }
71
  }