Решение на Пета задача от Георги Събев

Обратно към всички решения

Към профила на Георги Събев

Резултати

  • 3 точки от тестове
  • 0 бонус точки
  • 3 точки общо
  • 19 успешни тест(а)
  • 38 неуспешни тест(а)

Код

class Formatter
attr_reader :markdown
def initialize markdown, entities = nil
@markdown = markdown
@entities = entities || MarkdownParser.new(markdown).parse
end
def to_html
html = markdown
@entities.each do |entity|
occurrence = markdown[entity.start_index..entity.end_index]
html = html.sub(occurrence, entity.to_html)
end
html
end
alias to_s to_html
alias inspect markdown
end
class MarkdownParser
attr_reader :elements
def initialize markdown, element_types = nil
@markdown = markdown
@element_types = element_types ||
[Paragraph, Header, Quotation, CodeBlock, UnorderedList, OrderedList]
@elements = SortedSequence.new
end
def parse
element_list = @element_types.map { |elem_type| elem_type.elements @markdown }
@elements += element_list.flatten
end
end
class MarkdownEntity
attr_reader :raw_content, :content, :start_index, :end_index, :subelements
def initialize content, start_index, subelement_types,
raw_content = content, subcontent = raw_content
@raw_content, @content, @start_index = raw_content, content, start_index
@end_index = start_index + raw_content.length - 1
@subelements = MarkdownParser.new(subcontent, subelement_types).parse
end
def self.elements markdown
markdown.scan(pattern).map do |match|
create_entity match, markdown
end
end
def escape_html content
content.gsub('&', '&')
.gsub('<', '&lt;')
.gsub('>', '&gt;')
.gsub('"', '&quot;')
end
end
class Paragraph < MarkdownEntity
def initialize raw_content, start_index
super raw_content.strip, start_index, [Hyperlink, Strong, Emphasized], raw_content
end
def self.pattern
/(^(?!>|\s|\*|\d|\#{1,4}(?=\s[^\s])).*(\n(?!>|\s|\*|\d|\#{1,4}(?=\s)).*)*)/
end
def self.create_entity match, markdown
Paragraph.new match[0], markdown.index(match[0])
end
def to_html
html_content = Formatter.new(@content, subelements).to_html
"<p>#{escape_html(html_content)}</p>"
end
end
class Header < MarkdownEntity
attr_reader :size
def initialize raw_content, start_index, size, content
super content.strip, start_index, [Hyperlink, Strong, Emphasized], raw_content
@size = size
end
def self.pattern
/(^(\#{1,4}) ([^\s].*))/
end
def self.create_entity match, markdown
Header.new match[0], markdown.index(match[0]), match[1].size, match[2]
end
def to_html
html_content = Formatter.new(@content, subelements).to_html
"<h#{size}>#{escape_html(html_content)}</h#{size}>"
end
end
class Quotation < MarkdownEntity
def initialize raw_content, start_index
content = raw_content.gsub(/^>[ \t]*/m, '').gsub(/[ \t]*$/, '')
super content, start_index, [Paragraph], raw_content, content
end
def self.pattern
/(^(>\ +.*|^>)(\n(>\ +.*|^>))*)/
end
def self.create_entity match, markdown
Quotation.new match[0], markdown.index(match[0])
end
def to_html
html_content = Formatter.new(@content, subelements).to_html
"<blockquote>#{escape_html(html_content)}</blockquote>"
end
end
class CodeBlock < MarkdownEntity
def initialize raw_content, start_index
super raw_content.gsub(/^ {4}/, ''), start_index, [], raw_content
end
def self.pattern
/(^(?= {4}).*(\n(?= {4}).*)*)/
end
def self.create_entity match, markdown
CodeBlock.new match[0], markdown.index(match[0])
end
def to_html
"<pre><code>#{escape_html(@content)}</code></pre>"
end
end
class UnorderedList < MarkdownEntity
def initialize raw_content, start_index
content = raw_content.gsub(/^\* +/, '')
super content, start_index, [Hyperlink, Strong, Emphasized], raw_content
end
def self.pattern
/(^\*\s+.*(\n\*\s+.*)*)/
end
def self.create_entity match, markdown
UnorderedList.new match[0], markdown.index(match[0])
end
def to_html
html_content = Formatter.new(@content, subelements).to_html
items = html_content.lines.map { |li| " <li>#{escape_html(li.strip)}</li>" }
"<ul>\n#{items.join "\n"}\n</ul>"
end
end
class OrderedList < MarkdownEntity
def initialize raw_content, start_index
content = raw_content.gsub(/^\d\. +/, '')
super content, start_index, [Hyperlink, Strong, Emphasized], raw_content
end
def self.pattern
/(^\d\.\s+.*(\n\d\.\s+.*)*)/
end
def self.create_entity match, markdown
OrderedList.new match[0], markdown.index(match[0])
end
def to_html
html_content = Formatter.new(@content, subelements).to_html
items = html_content.lines.map { |li| " <li>#{escape_html(li.strip)}</li>" }
"<ol>\n#{items.join "\n"}\n</ol>"
end
end
class Hyperlink < MarkdownEntity
attr_reader :label, :hyperlink
def initialize raw_content, label, hyperlink, start_index
super raw_content, start_index, [Strong, Emphasized], raw_content, label
@label, @hyperlink = label, hyperlink
end
def self.pattern
/(\[([^]]*)\] \(([;:@&\.\/\w\d%#?=_-]*)\))/
end
def self.create_entity match, markdown
Hyperlink.new match[0], match[1], match[2], markdown.index(match[0])
end
def to_html
"<a href=\"#{hyperlink}\">#{escape_html(label)}</a>"
end
end
class Strong < MarkdownEntity
def initialize raw_content, start_index, content
super content.strip, start_index, [Emphasized], raw_content
end
def self.pattern
/(\*\*(.*)\*\*)/
end
def self.create_entity match, markdown
Strong.new match[0], markdown.index(match[0]), match[1]
end
def to_html
html_content = Formatter.new(@content, subelements).to_html
"<strong>#{escape_html(html_content)}</strong>"
end
end
class Emphasized < MarkdownEntity
def initialize raw_content, start_index, content
super content.strip, start_index, [Strong], raw_content
end
def self.pattern
/(_([^_\n]*)_)/
end
def self.create_entity match, markdown
Emphasized.new match[0], markdown.index(match[0]), match[1]
end
def to_html
html_content = Formatter.new(@content, subelements).to_html
"<em>#{escape_html(html_content)}</em>"
end
end
class SortedSequence
def initialize sequence = []
@sequence = sequence
end
def + sequence
SortedSequence.new(@sequence + sequence.map { |elem| [elem.start_index, elem] })
end
def each
@sequence.sort.each { |priority, value| yield value }
end
def [] index
@sequence[index][1]
end
end

Лог от изпълнението

...F...F...FF.F.FFFFFFFFF.FFFFFFFFFFFF.FFFFFF...FFFFF...F

Failures:

  1) Formatter paragraphs does not render empty paragraphs
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: ""
            got: "<p></p>"
       
       (compared using ==)
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:49:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  2) Formatter headers renders tricky ones
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<h2>Leading wsp</h2>"
            got: "   ## Leading wsp"
       
       (compared using ==)
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:665:in `block in expect_transformations'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:664:in `each'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:664:in `expect_transformations'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:106:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  3) Formatter code blocks renders multiline blocks with empty lines
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<pre><code>require 'gravity'\n\n# I'm flying! Just like in Python!</code></pre>"
            got: "<pre><code>require 'gravity'\n\n# I'm flying! Just like in Python!</code></pre>\n"
       
       (compared using ==)
       
       Diff:
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:140:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  4) Formatter code blocks renders multiple ones
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<pre><code>First code-block</code></pre>\n\n<pre><code>Second block of code</code></pre>"
            got: "<pre><code>First code-block</code></pre>\n\n<pre><code>Second block of code</code></pre>\n"
       
       (compared using ==)
       
       Diff:
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:156:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  5) Formatter code blocks renders properly a longer example with tabs and Unicode
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<pre><code>// \u041F\u0440\u0438\u043C\u0435\u0440 \u0437\u0430 \u0431\u043B\u043E\u043A \u0441 \u043A\u043E\u0434.\n// \u0412 \u043D\u0435\u0433\u043E \u0432\u0441\u0435\u043A\u0438 \u0440\u0435\u0434, \u0434\u043E\u0440\u0438 \u043F\u0440\u0430\u0437\u043D\u0438\u0442\u0435, \u0435 \u043F\u0440\u0435\u0434\u0448\u0435\u0441\u0442\u0432\u0430\u043D \u043E\u0442 \u0442\u043E\u0447\u043D\u043E \u0447\u0435\u0442\u0438\u0440\u0438 \u0438\u043D\u0442\u0435\u0440\u0432\u0430\u043B\u0430.\ninclude &lt;stdio.h&gt;\n\nint main(int, char**) {\n\t// Whitespace \u0441\u043B\u0435\u0434 \u0447\u0435\u0442\u0438\u0440\u0438\u0442\u0435 \u0437\u0430\u0434\u044A\u043B\u0436\u0438\u0442\u0435\u043B\u043D\u0438 \u0438\u043D\u0442\u0435\u0440\u0432\u0430\u043B\u0430 \u0432 \u043D\u0430\u0447\u0430\u043B\u043E\u0442\u043E, \u0441\u0435 \u0437\u0430\u043F\u0430\u0437\u0432\u0430 \u0432\u0438\u043D\u0430\u0433\u0438.\n\treturn 42;\n}</code></pre>"
            got: "<pre><code>// \u041F\u0440\u0438\u043C\u0435\u0440 \u0437\u0430 \u0431\u043B\u043E\u043A \u0441 \u043A\u043E\u0434.\n// \u0412 \u043D\u0435\u0433\u043E \u0432\u0441\u0435\u043A\u0438 \u0440\u0435\u0434, \u0434\u043E\u0440\u0438 \u043F\u0440\u0430\u0437\u043D\u0438\u0442\u0435, \u0435 \u043F\u0440\u0435\u0434\u0448\u0435\u0441\u0442\u0432\u0430\u043D \u043E\u0442 \u0442\u043E\u0447\u043D\u043E \u0447\u0435\u0442\u0438\u0440\u0438 \u0438\u043D\u0442\u0435\u0440\u0432\u0430\u043B\u0430.\ninclude &lt;stdio.h&gt;\n\nint main(int, char**) {\n\t// Whitespace \u0441\u043B\u0435\u0434 \u0447\u0435\u0442\u0438\u0440\u0438\u0442\u0435 \u0437\u0430\u0434\u044A\u043B\u0436\u0438\u0442\u0435\u043B\u043D\u0438 \u0438\u043D\u0442\u0435\u0440\u0432\u0430\u043B\u0430 \u0432 \u043D\u0430\u0447\u0430\u043B\u043E\u0442\u043E, \u0441\u0435 \u0437\u0430\u043F\u0430\u0437\u0432\u0430 \u0432\u0438\u043D\u0430\u0433\u0438.\n\treturn 42;\n}</code></pre>\n"
       
       (compared using ==)
       
       Diff:
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:186:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  6) Formatter blockquotes renders simple ones
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<blockquote><p>Simple quote</p></blockquote>"
            got: "<blockquote>&lt;p&gt;Simple quote&lt;/p&gt;</blockquote>"
       
       (compared using ==)
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:220:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  7) Formatter blockquotes renders multiline ones
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<blockquote><p>First line.\nSecond line.\nThird line.</p></blockquote>"
            got: "<blockquote>&lt;p&gt;First line.\nSecond line.\nThird line.&lt;/p&gt;</blockquote>\n"
       
       (compared using ==)
       
       Diff:
       
       @@ -1,4 +1,4 @@
       -<blockquote><p>First line.
       +<blockquote>&lt;p&gt;First line.
        Second line.
       -Third line.</p></blockquote>
       +Third line.&lt;/p&gt;</blockquote>
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:236:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  8) Formatter blockquotes renders multiple ones
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<blockquote><p>First quote.</p></blockquote>\n\n<blockquote><p>Second quote.</p></blockquote>"
            got: "<blockquote>&lt;p&gt;First quote.&lt;/p&gt;</blockquote>\n\n<blockquote>&lt;p&gt;Second quote.&lt;/p&gt;</blockquote>\n"
       
       (compared using ==)
       
       Diff:
       
       @@ -1,4 +1,4 @@
       -<blockquote><p>First quote.</p></blockquote>
       +<blockquote>&lt;p&gt;First quote.&lt;/p&gt;</blockquote>
        
       -<blockquote><p>Second quote.</p></blockquote>
       +<blockquote>&lt;p&gt;Second quote.&lt;/p&gt;</blockquote>
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:252:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  9) Formatter blockquotes renders multiline ones with multiple paragraphs
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<blockquote><p>First quote.</p>\n\n<p>Second quote.</p></blockquote>"
            got: "<blockquote>&lt;p&gt;First quote.&lt;/p&gt;\n\n&lt;p&gt;Second quote.&lt;/p&gt;</blockquote>\n"
       
       (compared using ==)
       
       Diff:
       
       @@ -1,4 +1,4 @@
       -<blockquote><p>First quote.</p>
       +<blockquote>&lt;p&gt;First quote.&lt;/p&gt;
        
       -<p>Second quote.</p></blockquote>
       +&lt;p&gt;Second quote.&lt;/p&gt;</blockquote>
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:268:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  10) Formatter blockquotes escapes special entities
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<blockquote><p>Cuttin &amp; Pastin, w/o Quotin (&quot;)</p></blockquote>"
            got: "<blockquote>&lt;p&gt;Cuttin &amp;amp; Pastin, w/o Quotin (&amp;quot;)&lt;/p&gt;</blockquote>"
       
       (compared using ==)
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:272:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  11) Formatter links renders simple links
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<p><a href=\"http://fmi.ruby.bg/\">Programming in Ruby</a></p>"
            got: "<p>[Programming in Ruby](http://fmi.ruby.bg/)</p>"
       
       (compared using ==)
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:278:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  12) Formatter links renders properly Unicode ones
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<p>\u0412\u044A\u043F\u0440\u043E\u0441? <a href=\"http://google.com/\">\u0418\u043C\u0430 Google</a> \u0437\u0430 \u0442\u0430\u0437\u0438 \u0446\u0435\u043B.</p>"
            got: "<p>\u0412\u044A\u043F\u0440\u043E\u0441? [\u0418\u043C\u0430 Google](http://google.com/) \u0437\u0430 \u0442\u0430\u0437\u0438 \u0446\u0435\u043B.</p>"
       
       (compared using ==)
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:282:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  13) Formatter links allows multiple links on a single line
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<p>We have <a href=\"some-url\">a first</a> and <a href=\"another-url\">Second</a>.</p>"
            got: "<p>We have [a first](some-url) and [Second](another-url).</p>"
       
       (compared using ==)
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:286:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  14) Formatter links does not render multiline or broken links
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<p>This one is [clearly] (broken)!</p>"
            got: "<p>This one is &lt;a href=&quot;broken&quot;&gt;clearly&lt;/a&gt;!</p>"
       
       (compared using ==)
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:665:in `block in expect_transformations'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:664:in `each'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:664:in `expect_transformations'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:295:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  15) Formatter links escapes special entities in the link description
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<p>Also testing <a href=\"here\">special &amp; &quot;entities&quot; &lt;b&gt;</a>.</p>"
            got: "<p>Also testing [special &amp; &quot;entities&quot; &lt;b&gt;](here).</p>"
       
       (compared using ==)
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:304:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  16) Formatter links escapes special entities in the link URL
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<p>Or <a href=\"special &amp; &quot;entities&quot; &lt;b&gt;\">what if</a> are in the URL, eh?</p>"
            got: "<p>Or [what if](special &amp; &quot;entities&quot; &lt;b&gt;) are in the URL, eh?</p>"
       
       (compared using ==)
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:309:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  17) Formatter lists renders simple unordered lists
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<ul>\n  <li>\u0415\u0434\u043D\u043E.</li>\n  <li>\u0414\u0440\u0443\u0433\u043E.</li>\n  <li>\u0422\u0440\u0435\u0442\u043E...</li>\n</ul>"
            got: "<ul>\n  <li>\u0415\u0434\u043D\u043E.</li>\n  <li>\u0414\u0440\u0443\u0433\u043E.</li>\n  <li>\u0422\u0440\u0435\u0442\u043E...</li>\n</ul>\n"
       
       (compared using ==)
       
       Diff:
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:330:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  18) Formatter lists renders simple ordered lists
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<ol>\n  <li>\u041F\u044A\u0440\u0432\u043E.</li>\n  <li>\u0412\u0442\u043E\u0440\u043E.</li>\n  <li>\u0422\u0440\u0435\u0442\u043E...</li>\n</ol>"
            got: "<ol>\n  <li>\u041F\u044A\u0440\u0432\u043E.</li>\n  <li>\u0412\u0442\u043E\u0440\u043E.</li>\n  <li>\u0422\u0440\u0435\u0442\u043E...</li>\n</ol>\n"
       
       (compared using ==)
       
       Diff:
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:348:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  19) Formatter lists renders lists with a single item
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<ul>\n  <li>Single item.</li>\n</ul>"
            got: "<ul>\n  <li>Single item.</li>\n</ul>\n"
       
       (compared using ==)
       
       Diff:
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:362:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  20) Formatter lists does not choke on malformed lists
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<p>1) \u041F\u044A\u0440\u0432\u043E.\n2 \u0412\u0442\u043E\u0440\u043E.\n3.\u0422\u0440\u0435\u0442\u043E</p>\n<ol>\n  <li>\u0427\u0435\u0442\u0432\u044A\u0440\u0442\u043E</li>\n</ol>"
            got: "1) \u041F\u044A\u0440\u0432\u043E.\n2 \u0412\u0442\u043E\u0440\u043E.\n3.\u0422\u0440\u0435\u0442\u043E\n<ol>\n  <li>\u0427\u0435\u0442\u0432\u044A\u0440\u0442\u043E</li>\n</ol>\n"
       
       (compared using ==)
       
       Diff:
       
       @@ -1,6 +1,6 @@
       -<p>1) Първо.
       +1) Първо.
        2 Второ.
       -3.Трето</p>
       +3.Трето
        <ol>
          <li>Четвърто</li>
        </ol>
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:394:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  21) Formatter lists escapes special entities in the list elements
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<ul>\n  <li>The &amp;&amp; and || are logical operators</li>\n  <li>The `&quot;` symbol</li>\n</ul>"
            got: "<ul>\n  <li>The &amp;&amp; and || are logical operators</li>\n  <li>The `&quot;` symbol</li>\n</ul>\n"
       
       (compared using ==)
       
       Diff:
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:410:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  22) Formatter lists allows links in list elements
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<ul>\n  <li>A <a href=\" here \">simple link</a> or there?</li>\n</ul>"
            got: "<ul>\n  <li>A [simple link]( here ) or there?</li>\n</ul>\n"
       
       (compared using ==)
       
       Diff:
       @@ -1,4 +1,4 @@
        <ul>
       -  <li>A <a href=" here ">simple link</a> or there?</li>
       +  <li>A [simple link]( here ) or there?</li>
        </ul>
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:424:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  23) Formatter bold and italic text rendering works in paragraphs
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<p><em>Simplest</em> case</p>"
            got: "<p>&lt;em&gt;Simplest&lt;/em&gt; case</p>"
       
       (compared using ==)
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:665:in `block in expect_transformations'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:664:in `each'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:664:in `expect_transformations'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:434:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  24) Formatter bold and italic text rendering allows multiple ones per line
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<p>Some <em>more words here</em> <em>to be</em> <strong>emphasized</strong>, okay?</p>"
            got: "<p>Some &lt;em&gt;more words here&lt;/em&gt; &lt;em&gt;to be&lt;/em&gt; &lt;strong&gt;emphasized&lt;/strong&gt;, okay?</p>"
       
       (compared using ==)
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:438:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  25) Formatter bold and italic text rendering works in headers
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<h1><em>Simplest</em> case</h1>"
            got: "<h1>_S&lt;em&gt;Simplest&lt;/em&gt;ase</h1>"
       
       (compared using ==)
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:665:in `block in expect_transformations'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:664:in `each'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:664:in `expect_transformations'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:447:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  26) Formatter bold and italic text rendering works in blockquotes
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<blockquote><p><em>Simplest</em> case</p></blockquote>"
            got: "<blockquote>&lt;p&gt;&amp;lt;em&amp;gt;Simplest&amp;lt;/em&amp;gt; case&lt;/p&gt;</blockquote>"
       
       (compared using ==)
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:665:in `block in expect_transformations'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:664:in `each'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:664:in `expect_transformations'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:455:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  27) Formatter bold and italic text rendering works in links
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<p>Some <a href=\"okay\"><em>more words here</em> <em>to be</em> <strong>emphasized</strong></a>?</p>"
            got: "<p>Some [&lt;em&gt;more words here&lt;/em&gt; &lt;em&gt;to be&lt;/em&gt; &lt;strong&gt;emphasized&lt;/strong&gt;](okay)?</p>"
       
       (compared using ==)
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:464:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  28) Formatter bold and italic text rendering works in list elements
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<ul>\n  <li>Some <em>more words</em> <em>to be</em> <strong>emphasized</strong></li>\n</ul>"
            got: "<ul>\n  <li>Some _m&lt;em&gt;more words&lt;/em&gt;t&lt;em&gt;to be&lt;/em&gt;*&lt;strong&gt;emphasized&lt;/strong&gt;</li>\n</ul>"
       
       (compared using ==)
       
       Diff:
       @@ -1,4 +1,4 @@
        <ul>
       -  <li>Some <em>more words</em> <em>to be</em> <strong>emphasized</strong></li>
       +  <li>Some _m&lt;em&gt;more words&lt;/em&gt;t&lt;em&gt;to be&lt;/em&gt;*&lt;strong&gt;emphasized&lt;/strong&gt;</li>
        </ul>
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:476:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  29) Formatter bold and italic text rendering works in links in list elements
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<ul>\n  <li>Some <a href=\"okay\"><em>more words</em> <em>to be</em> <strong>emphasized</strong></a>!</li>\n</ul>"
            got: "<ul>\n  <li>Some [_m&lt;em&gt;more words&lt;/em&gt;t&lt;em&gt;to be&lt;/em&gt;*&lt;strong&gt;emphasized&lt;/strong&gt;okay)!</li>\n</ul>"
       
       (compared using ==)
       
       Diff:
       @@ -1,4 +1,4 @@
        <ul>
       -  <li>Some <a href="okay"><em>more words</em> <em>to be</em> <strong>emphasized</strong></a>!</li>
       +  <li>Some [_m&lt;em&gt;more words&lt;/em&gt;t&lt;em&gt;to be&lt;/em&gt;*&lt;strong&gt;emphasized&lt;/strong&gt;okay)!</li>
        </ul>
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:487:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  30) Formatter bold and italic text rendering does not brake HTML entities inside it
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<p>Some <em>more &amp; words</em> <em>to be</em> <strong>&quot;emphasized&quot;</strong>!</p>"
            got: "<p>Some &lt;em&gt;more &amp;amp; words&lt;/em&gt; &lt;em&gt;to be&lt;/em&gt; &lt;strong&gt;&amp;quot;emphasized&amp;quot;&lt;/strong&gt;!</p>"
       
       (compared using ==)
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:491:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  31) Formatter bold and italic text rendering does not allow parial overlapping
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<p>Some <em>more words **to be</em> emphasized**!</p>"
            got: "<p>Some &lt;em&gt;more words **to be&lt;/em&gt; emphasized**!</p>"
       
       (compared using ==)
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:496:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  32) Formatter bold and italic text rendering allows simple nesting
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<p>Some <em>more words <strong>to be</strong> emphasized</em>!</p>"
            got: "<p>Some &lt;em&gt;more words *&amp;lt;strong&amp;gt;to be&amp;lt;/strong&amp;gt;emphasized&lt;/em&gt;!</p>"
       
       (compared using ==)
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:501:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  33) Formatter special entities escapes them in blockquotes
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<blockquote><p>&quot;Black &amp; Decker&quot;!</p></blockquote>"
            got: "<blockquote>&lt;p&gt;&amp;quot;Black &amp;amp; Decker&amp;quot;!&lt;/p&gt;</blockquote>"
       
       (compared using ==)
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:665:in `block in expect_transformations'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:664:in `each'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:664:in `expect_transformations'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:530:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  34) Formatter special entities escapes them in deeply-nested elements
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<h2><em>&quot;Black &amp; Decker&quot;</em>!</h2>"
            got: "<h2>_&quot;B&lt;em&gt;&amp;quot;Black &amp;amp; Decker&amp;quot;&lt;/em&gt;</h2>"
       
       (compared using ==)
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:665:in `block in expect_transformations'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:664:in `each'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:664:in `expect_transformations'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:536:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  35) Formatter whitespace removes excess leading and trailing whitespace
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<p>Some txt</p>"
            got: "\n\n<p>Some txt</p>"
       
       (compared using ==)
       
       Diff:
       @@ -1,2 +1,4 @@
       +
       +
        <p>Some txt</p>
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:665:in `block in expect_transformations'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:664:in `each'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:664:in `expect_transformations'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:547:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  36) Formatter whitespace ignores leading and trailing whitespace of lines whenever possible
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<p>A line here</p>"
            got: "   A line here   "
       
       (compared using ==)
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:665:in `block in expect_transformations'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:664:in `each'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:664:in `expect_transformations'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:555:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  37) Formatter whitespace does not touch trailing whitespace in code blocks
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<pre><code>First  \n  Second  </code></pre>"
            got: "<pre><code>First  \n  Second  </code></pre>\n\n"
       
       (compared using ==)
       
       Diff:
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:665:in `block in expect_transformations'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:664:in `each'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:664:in `expect_transformations'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:563:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

  38) Formatter mixed, complex input renders properly
     Failure/Error: Formatter.new(plain).to_html.should eq formatted.strip
       
       expected: "<h1>\u0426\u044F\u043B\u043E\u0441\u0442\u0435\u043D \u043F\u0440\u0438\u043C\u0435\u0440</h1>\n<p>\u0422\u0443\u043A \u0449\u0435 \u0434\u0435\u043C\u043E\u043D\u0441\u0442\u0440\u0438\u0440\u0430\u043C\u0435 \u043D\u0430\u043A\u0440\u0430\u0442\u043A\u043E \u0432\u044A\u0437\u043C\u043E\u0436\u043D\u043E\u0441\u0442\u0438\u0442\u0435 \u043D\u0430 \u043D\u0430\u0448\u0438\u044F \u043F\u0440\u043E\u0441\u0442 Markdown-\u043F\u0440\u0435\u043E\u0431\u0440\u0430\u0437\u0443\u0432\u0430\u0442\u0435\u043B.</p>\n\n<h2><em>\u0424\u0438\u043B\u043E\u0441\u043E\u0444\u0438\u044F</em> \u043D\u0430 <a href=\"http://daringfireball.net/projects/markdown/syntax#philosophy\">Markdown</a></h2>\n\n<p>\u041A\u0440\u0430\u0442\u044A\u043A \u0446\u0438\u0442\u0430\u0442 \u043E\u0442\u043D\u043E\u0441\u043D\u043E \u0444\u0438\u043B\u043E\u0441\u043E\u0444\u0438\u044F\u0442\u0430 \u043D\u0430 Markdown:</p>\n<blockquote><p>Markdown is intended to be as easy-to-read and easy-to-write as is feasible.</p>\n\n<p>Readability, however, is emphasized above all else. A Markdown-formatted document should be publishable as-is, as plain text, without looking like it\u2019s been marked up with tags or formatting instructions.</p></blockquote>\n<p>\u041F\u043E\u0432\u0435\u0447\u0435 \u0438\u043D\u0444\u043E\u0440\u043C\u0430\u0446\u0438\u044F \u043C\u043E\u0436\u0435 \u0434\u0430 \u043D\u0430\u043C\u0435\u0440\u0438\u0442\u0435 \u043D\u0430 <a href=\"http://daringfireball.net/projects/markdown\">\u0441\u0430\u0439\u0442\u0430 \u043D\u0430 <strong>Markdown</strong></a>.</p>\n\n<h2>\u041F\u0440\u0435\u0434\u0438\u043C\u0441\u0442\u0432\u0430</h2>\n\n<p>\u0421\u044A\u0437\u0434\u0430\u0432\u0430\u043D\u0435\u0442\u043E \u043D\u0430 \u0441\u044A\u0434\u044A\u0440\u0436\u0430\u043D\u0438\u0435 \u0432\u044A\u0432 \u0444\u043E\u0440\u043C\u0430\u0442\u0430 Markdown \u0438\u043C\u0430 \u043C\u043D\u043E\u0436\u0435\u0441\u0442\u0432\u043E \u043F\u0440\u0435\u0434\u0438\u043C\u0441\u0442\u0432\u0430.</p>\n\n<p>\u0415\u0442\u043E \u043D\u044F\u043A\u043E\u0438 \u043E\u0442 \u0442\u044F\u0445:</p>\n<ul>\n  <li>\u041B\u0435\u0441\u043D\u043E \u0447\u0435\u0442\u0438\u043C \u0432 <em>\u0441\u0443\u0440\u043E\u0432</em> \u0432\u0438\u0434</li>\n  <li>\u0411\u0435\u0437 &quot;\u0441\u043A\u0440\u0438\u0442\u0438&quot; \u0444\u043E\u0440\u043C\u0430\u0442\u0438\u0440\u0430\u0449\u0438 \u0442\u0430\u0433\u043E\u0432\u0435 \u2014 \u0444\u043E\u0440\u043C\u0430\u0442\u0438\u0440\u0430\u043D\u0435\u0442\u043E \u0432\u0438 \u043D\u0438\u043A\u043E\u0433\u0430 \u043D\u0435 \u0441\u0435 \u0447\u0443\u043F\u0438</li>\n  <li>\u0421\u043B\u0435\u0434 \u043E\u0431\u0440\u0430\u0431\u043E\u0442\u043A\u0430 \u043C\u043E\u0436\u0435 \u0434\u0430 \u0438\u0437\u0433\u043B\u0435\u0436\u0434\u0430 \u043C\u043D\u043E\u0433\u043E \u0434\u043E\u0431\u0440\u0435</li>\n</ul>\n\n<h2>\u041F\u043E\u0434\u0434\u0440\u044A\u0436\u043A\u0430 \u0432 <em>Ruby</em></h2>\n\n<p>\u0412 <strong>Ruby</strong> \u0438\u043C\u0430 \u043C\u043D\u043E\u0436\u0435\u0441\u0442\u0432\u043E Gem-\u043E\u0432\u0435, \u043A\u043E\u0438\u0442\u043E \u043C\u043E\u0433\u0430\u0442 \u0434\u0430 \u0432\u0438 \u043F\u043E\u043C\u043E\u0433\u043D\u0430\u0442 \u0437\u0430 \u0434\u0430 \u043F\u0440\u0435\u0445\u0432\u044A\u0440\u043B\u044F\u0442\u0435 Markdown-\u0441\u044A\u0434\u044A\u0440\u0436\u0430\u043D\u0438\u0435 \u0432 HTML-\u0444\u043E\u0440\u043C\u0430\u0442.\n\u041A\u043E\u0434\u044A\u0442, \u043A\u043E\u0439\u0442\u043E \u0432\u0438\u0435 \u0441\u044A\u0437\u0434\u0430\u0432\u0430\u0442\u0435, \u0441\u044A\u0449\u043E \u043C\u043E\u0436\u0435 \u0434\u0430 \u0432\u044A\u0440\u0448\u0438 \u0442\u043E\u0432\u0430 \u0434\u043E \u0438\u0437\u0432\u0435\u0441\u0442\u043D\u0430 \u0441\u0442\u0435\u043F\u0435\u043D.</p>\n\n<p>\u041F\u0440\u0438\u043C\u0435\u0440 \u0437\u0430 \u0443\u043F\u043E\u0442\u0440\u0435\u0431\u0430 \u043D\u0430 \u0432\u0430\u0448\u0438\u044F \u043A\u043E\u0434:</p>\n\n<pre><code># \u041C\u043D\u043E\u0433\u043E \u043F\u0440\u043E\u0441\u0442\u043E\nformatter = Formatter.new &quot;## My Markdown&quot;\nputs formatter.to_html</code></pre>"
            got: "<h1>\u0426\u044F\u043B\u043E\u0441\u0442\u0435\u043D \u043F\u0440\u0438\u043C\u0435\u0440</h1>\n<p>\u0422\u0443\u043A \u0449\u0435 \u0434\u0435\u043C\u043E\u043D\u0441\u0442\u0440\u0438\u0440\u0430\u043C\u0435 \u043D\u0430\u043A\u0440\u0430\u0442\u043A\u043E \u0432\u044A\u0437\u043C\u043E\u0436\u043D\u043E\u0441\u0442\u0438\u0442\u0435 \u043D\u0430 \u043D\u0430\u0448\u0438\u044F \u043F\u0440\u043E\u0441\u0442 Markdown-\u043F\u0440\u0435\u043E\u0431\u0440\u0430\u0437\u0443\u0432\u0430\u0442\u0435\u043B.</p>\n\n<h2>_\u0424\u0438&lt;em&gt;\u0424\u0438\u043B\u043E\u0441\u043E\u0444\u0438\u044F&lt;/em&gt; [Markdown](http://daringfireball.net/projects/markdown/syntax#philosophy)</h2>\n\n<p>\u041A\u0440\u0430\u0442\u044A\u043A \u0446\u0438\u0442\u0430\u0442 \u043E\u0442\u043D\u043E\u0441\u043D\u043E \u0444\u0438\u043B\u043E\u0441\u043E\u0444\u0438\u044F\u0442\u0430 \u043D\u0430 Markdown:</p>\n<blockquote>&lt;p&gt;Markdown is intended to be as easy-to-read and easy-to-write as is feasible.&lt;/p&gt;\n\n&lt;p&gt;Readability, however, is emphasized above all else. A Markdown-formatted document should be publishable as-is, as plain text, without looking like it\u2019s been marked up with tags or formatting instructions.&lt;/p&gt;</blockquote>\n<p>\u041F\u043E\u0432\u0435\u0447\u0435 \u0438\u043D\u0444\u043E\u0440\u043C\u0430\u0446\u0438\u044F \u043C\u043E\u0436\u0435 \u0434\u0430 \u043D\u0430\u043C\u0435\u0440\u0438\u0442\u0435 \u043D\u0430 [\u0441\u0430\u0439\u0442\u0430 \u043D\u0430 &lt;strong&gt;Markdown&lt;/strong&gt;](http://daringfireball.net/projects/markdown).</p>\n\n<h2>\u041F\u0440\u0435\u0434\u0438\u043C\u0441\u0442\u0432\u0430</h2>\n\n<p>\u0421\u044A\u0437\u0434\u0430\u0432\u0430\u043D\u0435\u0442\u043E \u043D\u0430 \u0441\u044A\u0434\u044A\u0440\u0436\u0430\u043D\u0438\u0435 \u0432\u044A\u0432 \u0444\u043E\u0440\u043C\u0430\u0442\u0430 Markdown \u0438\u043C\u0430 \u043C\u043D\u043E\u0436\u0435\u0441\u0442\u0432\u043E \u043F\u0440\u0435\u0434\u0438\u043C\u0441\u0442\u0432\u0430.</p>\n\n<p>\u0415\u0442\u043E \u043D\u044F\u043A\u043E\u0438 \u043E\u0442 \u0442\u044F\u0445:</p>\n<ul>\n  <li>\u041B\u0435\u0441\u043D\u043E \u0447\u0435\u0442\u0438\u043C \u0432 _\u0441&lt;em&gt;\u0441\u0443\u0440\u043E\u0432&lt;/em&gt;\u0438\u0434</li>\n  <li>\u0411\u0435\u0437 &quot;\u0441\u043A\u0440\u0438\u0442\u0438&quot; \u0444\u043E\u0440\u043C\u0430\u0442\u0438\u0440\u0430\u0449\u0438 \u0442\u0430\u0433\u043E\u0432\u0435 \u2014 \u0444\u043E\u0440\u043C\u0430\u0442\u0438\u0440\u0430\u043D\u0435\u0442\u043E \u0432\u0438 \u043D\u0438\u043A\u043E\u0433\u0430 \u043D\u0435 \u0441\u0435 \u0447\u0443\u043F\u0438</li>\n  <li>\u0421\u043B\u0435\u0434 \u043E\u0431\u0440\u0430\u0431\u043E\u0442\u043A\u0430 \u043C\u043E\u0436\u0435 \u0434\u0430 \u0438\u0437\u0433\u043B\u0435\u0436\u0434\u0430 \u043C\u043D\u043E\u0433\u043E \u0434\u043E\u0431\u0440\u0435</li>\n</ul>\n\n<h2>\u041F\u043E\u0434\u0434\u0440\u044A\u0436\u043A\u0430 \u0432 _Ru&lt;em&gt;Ruby&lt;/em&gt;</h2>\n\n<p>\u0412 &lt;strong&gt;Ruby&lt;/strong&gt; \u0438\u043C\u0430 \u043C\u043D\u043E\u0436\u0435\u0441\u0442\u0432\u043E Gem-\u043E\u0432\u0435, \u043A\u043E\u0438\u0442\u043E \u043C\u043E\u0433\u0430\u0442 \u0434\u0430 \u0432\u0438 \u043F\u043E\u043C\u043E\u0433\u043D\u0430\u0442 \u0437\u0430 \u0434\u0430 \u043F\u0440\u0435\u0445\u0432\u044A\u0440\u043B\u044F\u0442\u0435 Markdown-\u0441\u044A\u0434\u044A\u0440\u0436\u0430\u043D\u0438\u0435 \u0432 HTML-\u0444\u043E\u0440\u043C\u0430\u0442.\n\u041A\u043E\u0434\u044A\u0442, \u043A\u043E\u0439\u0442\u043E \u0432\u0438\u0435 \u0441\u044A\u0437\u0434\u0430\u0432\u0430\u0442\u0435, \u0441\u044A\u0449\u043E \u043C\u043E\u0436\u0435 \u0434\u0430 \u0432\u044A\u0440\u0448\u0438 \u0442\u043E\u0432\u0430 \u0434\u043E \u0438\u0437\u0432\u0435\u0441\u0442\u043D\u0430 \u0441\u0442\u0435\u043F\u0435\u043D.</p>\n\n<p>\u041F\u0440\u0438\u043C\u0435\u0440 \u0437\u0430 \u0443\u043F\u043E\u0442\u0440\u0435\u0431\u0430 \u043D\u0430 \u0432\u0430\u0448\u0438\u044F \u043A\u043E\u0434:</p>\n\n<pre><code># \u041C\u043D\u043E\u0433\u043E \u043F\u0440\u043E\u0441\u0442\u043E\nformatter = Formatter.new &quot;## My Markdown&quot;\nputs formatter.to_html</code></pre>\n"
       
       (compared using ==)
       
       Diff:
       
       
       @@ -1,13 +1,13 @@
        <h1>Цялостен пример</h1>
        <p>Тук ще демонстрираме накратко възможностите на нашия прост Markdown-преобразувател.</p>
        
       -<h2><em>Философия</em> на <a href="http://daringfireball.net/projects/markdown/syntax#philosophy">Markdown</a></h2>
       +<h2>_Фи&lt;em&gt;Философия&lt;/em&gt; [Markdown](http://daringfireball.net/projects/markdown/syntax#philosophy)</h2>
        
        <p>Кратък цитат относно философията на Markdown:</p>
       -<blockquote><p>Markdown is intended to be as easy-to-read and easy-to-write as is feasible.</p>
       +<blockquote>&lt;p&gt;Markdown is intended to be as easy-to-read and easy-to-write as is feasible.&lt;/p&gt;
        
       -<p>Readability, however, is emphasized above all else. A Markdown-formatted document should be publishable as-is, as plain text, without looking like it’s been marked up with tags or formatting instructions.</p></blockquote>
       -<p>Повече информация може да намерите на <a href="http://daringfireball.net/projects/markdown">сайта на <strong>Markdown</strong></a>.</p>
       +&lt;p&gt;Readability, however, is emphasized above all else. A Markdown-formatted document should be publishable as-is, as plain text, without looking like it’s been marked up with tags or formatting instructions.&lt;/p&gt;</blockquote>
       +<p>Повече информация може да намерите на [сайта на &lt;strong&gt;Markdown&lt;/strong&gt;](http://daringfireball.net/projects/markdown).</p>
        
        <h2>Предимства</h2>
        
       
       
       @@ -15,14 +15,14 @@
        
        <p>Ето някои от тях:</p>
        <ul>
       -  <li>Лесно четим в <em>суров</em> вид</li>
       +  <li>Лесно четим в _с&lt;em&gt;суров&lt;/em&gt;ид</li>
          <li>Без &quot;скрити&quot; форматиращи тагове — форматирането ви никога не се чупи</li>
          <li>След обработка може да изглежда много добре</li>
        </ul>
        
       -<h2>Поддръжка в <em>Ruby</em></h2>
       +<h2>Поддръжка в _Ru&lt;em&gt;Ruby&lt;/em&gt;</h2>
        
       -<p>В <strong>Ruby</strong> има множество Gem-ове, които могат да ви помогнат за да прехвърляте Markdown-съдържание в HTML-формат.
       +<p>В &lt;strong&gt;Ruby&lt;/strong&gt; има множество Gem-ове, които могат да ви помогнат за да прехвърляте Markdown-съдържание в HTML-формат.
        Кодът, който вие създавате, също може да върши това до известна степен.</p>
        
        <p>Пример за употреба на вашия код:</p>
     # /tmp/d20111129-16859-1teqtdo/spec.rb:660:in `expect_transformation'
     # /tmp/d20111129-16859-1teqtdo/spec.rb:655:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (3 levels) in <top (required)>'
     # ./lib/homework/run_with_timeout.rb:5:in `block (2 levels) in <top (required)>'

Finished in 0.65624 seconds
57 examples, 38 failures

Failed examples:

rspec /tmp/d20111129-16859-1teqtdo/spec.rb:48 # Formatter paragraphs does not render empty paragraphs
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:99 # Formatter headers renders tricky ones
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:127 # Formatter code blocks renders multiline blocks with empty lines
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:143 # Formatter code blocks renders multiple ones
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:163 # Formatter code blocks renders properly a longer example with tabs and Unicode
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:219 # Formatter blockquotes renders simple ones
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:223 # Formatter blockquotes renders multiline ones
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:239 # Formatter blockquotes renders multiple ones
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:255 # Formatter blockquotes renders multiline ones with multiple paragraphs
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:271 # Formatter blockquotes escapes special entities
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:277 # Formatter links renders simple links
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:281 # Formatter links renders properly Unicode ones
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:285 # Formatter links allows multiple links on a single line
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:290 # Formatter links does not render multiline or broken links
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:303 # Formatter links escapes special entities in the link description
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:308 # Formatter links escapes special entities in the link URL
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:315 # Formatter lists renders simple unordered lists
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:333 # Formatter lists renders simple ordered lists
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:351 # Formatter lists renders lists with a single item
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:377 # Formatter lists does not choke on malformed lists
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:397 # Formatter lists escapes special entities in the list elements
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:413 # Formatter lists allows links in list elements
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:429 # Formatter bold and italic text rendering works in paragraphs
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:437 # Formatter bold and italic text rendering allows multiple ones per line
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:442 # Formatter bold and italic text rendering works in headers
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:450 # Formatter bold and italic text rendering works in blockquotes
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:463 # Formatter bold and italic text rendering works in links
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:468 # Formatter bold and italic text rendering works in list elements
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:479 # Formatter bold and italic text rendering works in links in list elements
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:490 # Formatter bold and italic text rendering does not brake HTML entities inside it
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:495 # Formatter bold and italic text rendering does not allow parial overlapping
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:500 # Formatter bold and italic text rendering allows simple nesting
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:527 # Formatter special entities escapes them in blockquotes
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:533 # Formatter special entities escapes them in deeply-nested elements
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:541 # Formatter whitespace removes excess leading and trailing whitespace
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:550 # Formatter whitespace ignores leading and trailing whitespace of lines whenever possible
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:558 # Formatter whitespace does not touch trailing whitespace in code blocks
rspec /tmp/d20111129-16859-1teqtdo/spec.rb:586 # Formatter mixed, complex input renders properly

История (1 версия и 0 коментара)

Георги обнови решението на 23.11.2011 17:43 (преди над 12 години)

+class Formatter
+ attr_reader :markdown
+
+ def initialize markdown, entities = nil
+ @markdown = markdown
+ @entities = entities || MarkdownParser.new(markdown).parse
+ end
+
+ def to_html
+ html = markdown
+ @entities.each do |entity|
+ occurrence = markdown[entity.start_index..entity.end_index]
+ html = html.sub(occurrence, entity.to_html)
+ end
+ html
+ end
+
+ alias to_s to_html
+ alias inspect markdown
+end
+
+class MarkdownParser
+ attr_reader :elements
+
+ def initialize markdown, element_types = nil
+ @markdown = markdown
+ @element_types = element_types ||
+ [Paragraph, Header, Quotation, CodeBlock, UnorderedList, OrderedList]
+ @elements = SortedSequence.new
+ end
+
+ def parse
+ element_list = @element_types.map { |elem_type| elem_type.elements @markdown }
+ @elements += element_list.flatten
+ end
+end
+
+class MarkdownEntity
+ attr_reader :raw_content, :content, :start_index, :end_index, :subelements
+
+ def initialize content, start_index, subelement_types,
+ raw_content = content, subcontent = raw_content
+ @raw_content, @content, @start_index = raw_content, content, start_index
+ @end_index = start_index + raw_content.length - 1
+ @subelements = MarkdownParser.new(subcontent, subelement_types).parse
+ end
+
+ def self.elements markdown
+ markdown.scan(pattern).map do |match|
+ create_entity match, markdown
+ end
+ end
+
+ def escape_html content
+ content.gsub('&', '&amp;')
+ .gsub('<', '&lt;')
+ .gsub('>', '&gt;')
+ .gsub('"', '&quot;')
+ end
+end
+
+class Paragraph < MarkdownEntity
+ def initialize raw_content, start_index
+ super raw_content.strip, start_index, [Hyperlink, Strong, Emphasized], raw_content
+ end
+
+ def self.pattern
+ /(^(?!>|\s|\*|\d|\#{1,4}(?=\s[^\s])).*(\n(?!>|\s|\*|\d|\#{1,4}(?=\s)).*)*)/
+ end
+
+ def self.create_entity match, markdown
+ Paragraph.new match[0], markdown.index(match[0])
+ end
+
+ def to_html
+ html_content = Formatter.new(@content, subelements).to_html
+ "<p>#{escape_html(html_content)}</p>"
+ end
+end
+
+class Header < MarkdownEntity
+ attr_reader :size
+
+ def initialize raw_content, start_index, size, content
+ super content.strip, start_index, [Hyperlink, Strong, Emphasized], raw_content
+ @size = size
+ end
+
+ def self.pattern
+ /(^(\#{1,4}) ([^\s].*))/
+ end
+
+ def self.create_entity match, markdown
+ Header.new match[0], markdown.index(match[0]), match[1].size, match[2]
+ end
+
+ def to_html
+ html_content = Formatter.new(@content, subelements).to_html
+ "<h#{size}>#{escape_html(html_content)}</h#{size}>"
+ end
+end
+
+class Quotation < MarkdownEntity
+ def initialize raw_content, start_index
+ content = raw_content.gsub(/^>[ \t]*/m, '').gsub(/[ \t]*$/, '')
+ super content, start_index, [Paragraph], raw_content, content
+ end
+
+ def self.pattern
+ /(^(>\ +.*|^>)(\n(>\ +.*|^>))*)/
+ end
+
+ def self.create_entity match, markdown
+ Quotation.new match[0], markdown.index(match[0])
+ end
+
+ def to_html
+ html_content = Formatter.new(@content, subelements).to_html
+ "<blockquote>#{escape_html(html_content)}</blockquote>"
+ end
+end
+
+class CodeBlock < MarkdownEntity
+ def initialize raw_content, start_index
+ super raw_content.gsub(/^ {4}/, ''), start_index, [], raw_content
+ end
+
+ def self.pattern
+ /(^(?= {4}).*(\n(?= {4}).*)*)/
+ end
+
+ def self.create_entity match, markdown
+ CodeBlock.new match[0], markdown.index(match[0])
+ end
+
+ def to_html
+ "<pre><code>#{escape_html(@content)}</code></pre>"
+ end
+end
+
+class UnorderedList < MarkdownEntity
+ def initialize raw_content, start_index
+ content = raw_content.gsub(/^\* +/, '')
+ super content, start_index, [Hyperlink, Strong, Emphasized], raw_content
+ end
+
+ def self.pattern
+ /(^\*\s+.*(\n\*\s+.*)*)/
+ end
+
+ def self.create_entity match, markdown
+ UnorderedList.new match[0], markdown.index(match[0])
+ end
+
+ def to_html
+ html_content = Formatter.new(@content, subelements).to_html
+ items = html_content.lines.map { |li| " <li>#{escape_html(li.strip)}</li>" }
+ "<ul>\n#{items.join "\n"}\n</ul>"
+ end
+end
+
+class OrderedList < MarkdownEntity
+ def initialize raw_content, start_index
+ content = raw_content.gsub(/^\d\. +/, '')
+ super content, start_index, [Hyperlink, Strong, Emphasized], raw_content
+ end
+
+ def self.pattern
+ /(^\d\.\s+.*(\n\d\.\s+.*)*)/
+ end
+
+ def self.create_entity match, markdown
+ OrderedList.new match[0], markdown.index(match[0])
+ end
+
+ def to_html
+ html_content = Formatter.new(@content, subelements).to_html
+ items = html_content.lines.map { |li| " <li>#{escape_html(li.strip)}</li>" }
+ "<ol>\n#{items.join "\n"}\n</ol>"
+ end
+end
+
+class Hyperlink < MarkdownEntity
+ attr_reader :label, :hyperlink
+
+ def initialize raw_content, label, hyperlink, start_index
+ super raw_content, start_index, [Strong, Emphasized], raw_content, label
+ @label, @hyperlink = label, hyperlink
+ end
+
+ def self.pattern
+ /(\[([^]]*)\] \(([;:@&\.\/\w\d%#?=_-]*)\))/
+ end
+
+ def self.create_entity match, markdown
+ Hyperlink.new match[0], match[1], match[2], markdown.index(match[0])
+ end
+
+ def to_html
+ "<a href=\"#{hyperlink}\">#{escape_html(label)}</a>"
+ end
+end
+
+class Strong < MarkdownEntity
+ def initialize raw_content, start_index, content
+ super content.strip, start_index, [Emphasized], raw_content
+ end
+
+ def self.pattern
+ /(\*\*(.*)\*\*)/
+ end
+
+ def self.create_entity match, markdown
+ Strong.new match[0], markdown.index(match[0]), match[1]
+ end
+
+ def to_html
+ html_content = Formatter.new(@content, subelements).to_html
+ "<strong>#{escape_html(html_content)}</strong>"
+ end
+end
+
+class Emphasized < MarkdownEntity
+ def initialize raw_content, start_index, content
+ super content.strip, start_index, [Strong], raw_content
+ end
+
+ def self.pattern
+ /(_([^_\n]*)_)/
+ end
+
+ def self.create_entity match, markdown
+ Emphasized.new match[0], markdown.index(match[0]), match[1]
+ end
+
+ def to_html
+ html_content = Formatter.new(@content, subelements).to_html
+ "<em>#{escape_html(html_content)}</em>"
+ end
+end
+
+class SortedSequence
+
+ def initialize sequence = []
+ @sequence = sequence
+ end
+
+ def + sequence
+ SortedSequence.new(@sequence + sequence.map { |elem| [elem.start_index, elem] })
+ end
+
+ def each
+ @sequence.sort.each { |priority, value| yield value }
+ end
+
+ def [] index
+ @sequence[index][1]
+ end
+end
+