How to select first 280 words of text up to the closest period?

Viewed 66

I need to extract a shorter segment of text of a specified number of words from a longer one. I can do this using

text = "There was a very big cat that was sitting on the ledge. It was  overlooking the garden. The dog next door watched with curiosity."

    text.split[0..15].join(' ')
    >>""There was a very big cat that was sitting on the ledge. It was  overlooking"

I would like to select the text up to the next period so I don't end up with a partial sentence.

Is there a way possibly using a Regex to accomplish what I'm trying to do that will be able to get the text up to and including the closest next period after the 15th word?

3 Answers

You can use

(?:\w+[,.?!]?\s+){14}(?:\w+,?\s+)*?\w+[.?!]

Repeats a word, optional [comma/period/question mark/exclamation mark], and spaces, 14 times. Then, it lazy-repeats a word followed by a space, followed by another word and a period, ensuring that the pattern ends at the first period after 15 words from the start.

https://regex101.com/r/ardIQ7/4

r = /
    (?:           # begin a non-capture group
      \p{Alpha}+  # match one or more letters
      [.!?]?      # optionally ('?' following ']') match one of the 3 punctuation chars
      [ ]+        # match one or more spaces
    )             # end non-capture group
    {14,}?        # execute the preceding non-capture group at least 14 times, lazily ('?')
    \p{Alpha}+    # match one or more letters  
    [.!?]         # match one of the three punctuation characters
    /x            # free-spacing regex definition mode

text[r]
  #=> "There was a very big cat that was sitting on the ledge. It was overlooking 
  #    the garden.

Free-spacing mode strips out spaces, which is why the space character above is in a character class ([ ]+). Written conventionally, the regex is as follows.

/(?:\p{Alpha}+[.!?]? +){14,}?\p{Alpha}+[.!?]/

You can do something along these lines:

text = "There was a very big cat that was sitting on the ledge. It was  overlooking the garden. The dog next door watched with curiosity."

tgt=15
old_text=text.scan(/[^.]+\.\s?/)
new_text=[]
while (old_text && new_text.join.scan(/\b\p{Alpha}+\b/).length<=tgt) do
   new_text << old_text.shift
end   

p new_text.join

Prints:

"There was a very big cat that was sitting on the ledge. It was  overlooking the garden. "

That works with any length of normal sentences and will break as soon as 1 additional sentence exceeds the word target.

Related