[User]
Task

Find the *character* and *byte* length of a string.

This means encodings like UTF-8 need to be handled properly, as there is not necessarily a one-to-one relationship between bytes and characters.

By *character*, we mean an individual Unicode *code point*, not a user-visible *grapheme* containing combining characters.

For example, the character length of "møøse" is 5 but the byte length is 7 in UTF-8 and 10 in UTF-16.

Non-BMP code points (those between 0x10000 and 0x10FFFF) must also be handled correctly: answers should produce actual character counts in code points, not in code unit counts.

Therefore a string like "𝔘𝔫𝔦𝔠𝔬𝔡𝔢" (consisting of the 7 Unicode characters U+1D518 U+1D52B U+1D526 U+1D520 U+1D52C U+1D521 U+1D522) is 7 characters long, **not** 14 UTF-16 code units; and it is 28 bytes long whether encoded in UTF-8 or in UTF-16.

Please mark your examples with ===Character Length=== or ===Byte Length===.

If your language is capable of providing the string length in graphemes, mark those examples with ===Grapheme Length===.

For example, the string "J̲o̲s̲é̲" ("J\x{332}o\x{332}s\x{332}e\x{301}\x{332}") has 4 user-visible graphemes, 9 characters (code points), and 14 bytes when encoded in UTF-8.

Other tasks related to string operations:

Metrics

* Array length
* String length
* Copy a string
* Empty string  (assignment)

Counting

* Word frequency
* Letter frequency
* Jewels and stones
* I before E except after C
* Bioinformatics/base count
* Count occurrences of a substring
* Count how many vowels and consonants occur in a string

Remove/replace

* XXXX redacted
* Conjugate a Latin verb
* Remove vowels from a string
* String interpolation (included)
* Strip block comments
* Strip comments from a string
* Strip a set of characters from a string
* Strip whitespace from a string -- top and tail
* Strip control codes and extended characters from a string

Anagrams/Derangements/shuffling

* Word wheel
* ABC problem
* Sattolo cycle
* Knuth shuffle
* Ordered words
* Superpermutation minimisation
* Textonyms (using a phone text pad)
* Anagrams
* Anagrams/Deranged anagrams
* Permutations/Derangements

Find/Search/Determine

* ABC words
* Odd words
* Word ladder
* Semordnilap
* Word search
* Wordiff  (game)
* String matching
* Tea cup rim text
* Alternade words
* Changeable words
* State name puzzle
* String comparison
* Unique characters
* Unique characters in each string
* Extract file extension
* Levenshtein distance
* Palindrome detection
* Common list elements
* Longest common suffix
* Longest common prefix
* Compare a list of strings
* Longest common substring
* Find common directory path
* Words from neighbour ones
* Change e letters to i in words
* Non-continuous subsequences
* Longest common subsequence
* Longest palindromic substrings
* Longest increasing subsequence
* Words containing "the" substring
* Sum of the digits of n is substring of n
* Determine if a string is numeric
* Determine if a string is collapsible
* Determine if a string is squeezable
* Determine if a string has all unique characters
* Determine if a string has all the same characters
* Longest substrings without repeating characters
* Find words which contains all the vowels
* Find words which contain the most consonants
* Find words which contains more than 3 vowels
* Find words whose first and last three letters are equal
* Find words with alternating vowels and consonants

Formatting

* Substring
* Rep-string
* Word wrap
* String case
* Align columns
* Literals/String
* Repeat a string
* Brace expansion
* Brace expansion using ranges
* Reverse a string
* Phrase reversals
* Comma quibbling
* Special characters
* String concatenation
* Substring/Top and tail
* Commatizing numbers
* Reverse words in a string
* Suffixation of decimal numbers
* Long literals, with continuations
* Numerical and alphabetical suffixes
* Abbreviations, easy
* Abbreviations, simple
* Abbreviations, automatic

Song lyrics/poems/Mad Libs/phrases

* Mad Libs
* Magic 8-ball
* 99 bottles of beer
* The Name Game (a song)
* The Old lady swallowed a fly
* The Twelve Days of Christmas

Tokenize

* Text between
* Tokenize a string
* Word break problem
* Tokenize a string with escaping
* Split a character string based on change of character

Sequences

* Show ASCII table
* De Bruijn sequences
* Summarize and say sequence
* Generate lower case ASCII alphabet

[Assistant]
(formerly Perl 6)

### Byte Length

```
say 'møøse'.encode('UTF-8').bytes;
```

### Character Length

```
say 'møøse'.codes;
```

### Grapheme Length

```
say 'møøse'.chars;
```


[User]
Task

Given two strings, demonstrate the following three types of string matching:

:   :   1. Determining if the first string starts with second string
        2. Determining if the first string contains the second string at any location
        3. Determining if the first string ends with the second string

Optional requirements:

:   :   1. Print the location of the match for part 2
        2. Handle multiple occurrences of a string for part 2.

Other tasks related to string operations:

Metrics

* Array length
* String length
* Copy a string
* Empty string  (assignment)

Counting

* Word frequency
* Letter frequency
* Jewels and stones
* I before E except after C
* Bioinformatics/base count
* Count occurrences of a substring
* Count how many vowels and consonants occur in a string

Remove/replace

* XXXX redacted
* Conjugate a Latin verb
* Remove vowels from a string
* String interpolation (included)
* Strip block comments
* Strip comments from a string
* Strip a set of characters from a string
* Strip whitespace from a string -- top and tail
* Strip control codes and extended characters from a string

Anagrams/Derangements/shuffling

* Word wheel
* ABC problem
* Sattolo cycle
* Knuth shuffle
* Ordered words
* Superpermutation minimisation
* Textonyms (using a phone text pad)
* Anagrams
* Anagrams/Deranged anagrams
* Permutations/Derangements

Find/Search/Determine

* ABC words
* Odd words
* Word ladder
* Semordnilap
* Word search
* Wordiff  (game)
* String matching
* Tea cup rim text
* Alternade words
* Changeable words
* State name puzzle
* String comparison
* Unique characters
* Unique characters in each string
* Extract file extension
* Levenshtein distance
* Palindrome detection
* Common list elements
* Longest common suffix
* Longest common prefix
* Compare a list of strings
* Longest common substring
* Find common directory path
* Words from neighbour ones
* Change e letters to i in words
* Non-continuous subsequences
* Longest common subsequence
* Longest palindromic substrings
* Longest increasing subsequence
* Words containing "the" substring
* Sum of the digits of n is substring of n
* Determine if a string is numeric
* Determine if a string is collapsible
* Determine if a string is squeezable
* Determine if a string has all unique characters
* Determine if a string has all the same characters
* Longest substrings without repeating characters
* Find words which contains all the vowels
* Find words which contain the most consonants
* Find words which contains more than 3 vowels
* Find words whose first and last three letters are equal
* Find words with alternating vowels and consonants

Formatting

* Substring
* Rep-string
* Word wrap
* String case
* Align columns
* Literals/String
* Repeat a string
* Brace expansion
* Brace expansion using ranges
* Reverse a string
* Phrase reversals
* Comma quibbling
* Special characters
* String concatenation
* Substring/Top and tail
* Commatizing numbers
* Reverse words in a string
* Suffixation of decimal numbers
* Long literals, with continuations
* Numerical and alphabetical suffixes
* Abbreviations, easy
* Abbreviations, simple
* Abbreviations, automatic

Song lyrics/poems/Mad Libs/phrases

* Mad Libs
* Magic 8-ball
* 99 bottles of beer
* The Name Game (a song)
* The Old lady swallowed a fly
* The Twelve Days of Christmas

Tokenize

* Text between
* Tokenize a string
* Word break problem
* Tokenize a string with escaping
* Split a character string based on change of character

Sequences

* Show ASCII table
* De Bruijn sequences
* Summarize and say sequence
* Generate lower case ASCII alphabet

[Assistant]
(formerly Perl 6)

Using string methods:

```
$haystack.starts-with($needle)  # True if $haystack starts with $needle
$haystack.contains($needle)     # True if $haystack contains $needle
$haystack.ends-with($needle)    # True if $haystack ends with $needle
```

Using regexes:

```
so $haystack ~~ /^ $needle  /  # True if $haystack starts with $needle
so $haystack ~~ /  $needle  /  # True if $haystack contains $needle
so $haystack ~~ /  $needle $/  # True if $haystack ends with $needle
```

Using `substr`:

```
substr($haystack, 0, $needle.chars) eq $needle  # True if $haystack starts with $needle
substr($haystack, *-$needle.chars) eq $needle   # True if $haystack ends with $needle
```

Bonus task:

```
$haystack.match($needle, :g)».from;  # List of all positions where $needle appears in $haystack
$haystack.indices($needle :overlap); # Also find any overlapping instances of $needle in $haystack
```


[User]
Task

Create a string variable equal to any text value.

Prepend the string variable with another string literal.

If your language supports any idiomatic ways to do this without referring to the variable twice in one expression, include such solutions.

To illustrate the operation, show the content of the variable.

[Assistant]
(formerly Perl 6)

```
# explicit concatentation
$_ = 'byte';
$_ = 'kilo' ~ $_;
.say;

# interpolation as concatenation
$_ = 'buck';
$_ = "mega$_";
.say;

# lvalue substr
$_ = 'bit';
substr-rw($_,0,0) = 'nano';
.say;

# regex substitution
$_ = 'fortnight';
s[^] = 'micro';
.say;

# reversed append assignment
$_ = 'cooper';
$_ [R~]= 'mini';
.say;

```

Output:

```
kilobyte
megabuck
nanobit
microfortnight
minicooper
```


[User]
Task

Create a function that strips a set of characters from a string.

The function should take two arguments:

:   :   :   1. a string to be stripped
            2. a string containing the set of characters to be stripped

The returned string should contain the first string, stripped of any characters in the second argument:

```
 print stripchars("She was a soul stripper. She took my heart!","aei")
Sh ws  soul strppr. Sh took my hrt!
```

Other tasks related to string operations:

Metrics

* Array length
* String length
* Copy a string
* Empty string  (assignment)

Counting

* Word frequency
* Letter frequency
* Jewels and stones
* I before E except after C
* Bioinformatics/base count
* Count occurrences of a substring
* Count how many vowels and consonants occur in a string

Remove/replace

* XXXX redacted
* Conjugate a Latin verb
* Remove vowels from a string
* String interpolation (included)
* Strip block comments
* Strip comments from a string
* Strip a set of characters from a string
* Strip whitespace from a string -- top and tail
* Strip control codes and extended characters from a string

Anagrams/Derangements/shuffling

* Word wheel
* ABC problem
* Sattolo cycle
* Knuth shuffle
* Ordered words
* Superpermutation minimisation
* Textonyms (using a phone text pad)
* Anagrams
* Anagrams/Deranged anagrams
* Permutations/Derangements

Find/Search/Determine

* ABC words
* Odd words
* Word ladder
* Semordnilap
* Word search
* Wordiff  (game)
* String matching
* Tea cup rim text
* Alternade words
* Changeable words
* State name puzzle
* String comparison
* Unique characters
* Unique characters in each string
* Extract file extension
* Levenshtein distance
* Palindrome detection
* Common list elements
* Longest common suffix
* Longest common prefix
* Compare a list of strings
* Longest common substring
* Find common directory path
* Words from neighbour ones
* Change e letters to i in words
* Non-continuous subsequences
* Longest common subsequence
* Longest palindromic substrings
* Longest increasing subsequence
* Words containing "the" substring
* Sum of the digits of n is substring of n
* Determine if a string is numeric
* Determine if a string is collapsible
* Determine if a string is squeezable
* Determine if a string has all unique characters
* Determine if a string has all the same characters
* Longest substrings without repeating characters
* Find words which contains all the vowels
* Find words which contain the most consonants
* Find words which contains more than 3 vowels
* Find words whose first and last three letters are equal
* Find words with alternating vowels and consonants

Formatting

* Substring
* Rep-string
* Word wrap
* String case
* Align columns
* Literals/String
* Repeat a string
* Brace expansion
* Brace expansion using ranges
* Reverse a string
* Phrase reversals
* Comma quibbling
* Special characters
* String concatenation
* Substring/Top and tail
* Commatizing numbers
* Reverse words in a string
* Suffixation of decimal numbers
* Long literals, with continuations
* Numerical and alphabetical suffixes
* Abbreviations, easy
* Abbreviations, simple
* Abbreviations, automatic

Song lyrics/poems/Mad Libs/phrases

* Mad Libs
* Magic 8-ball
* 99 bottles of beer
* The Name Game (a song)
* The Old lady swallowed a fly
* The Twelve Days of Christmas

Tokenize

* Text between
* Tokenize a string
* Word break problem
* Tokenize a string with escaping
* Split a character string based on change of character

Sequences

* Show ASCII table
* De Bruijn sequences
* Summarize and say sequence
* Generate lower case ASCII alphabet

[Assistant]
(formerly Perl 6)

```
sub strip_chars ( $s, $chars ) {
    return $s.trans( $chars.comb X=> '' );
}

say strip_chars( 'She was a soul stripper. She took my heart!', 'aei' );

```

Output:

```
Sh ws  soul strppr. Sh took my hrt!
```


[User]
A block comment begins with a   *beginning delimiter*   and ends with a   *ending delimiter*,   including the delimiters.   These delimiters are often multi-character sequences.

Task

Strip block comments from program text (of a programming language much like classic C).

Your demos should at least handle simple, non-nested and multi-line block comment delimiters.

The block comment delimiters are the two-character sequences:

:   :   :   * **/\***      (beginning delimiter)
            * **\*/**      (ending delimiter)

Sample text for stripping:

```
  /**
   * Some comments
   * longer comments here that we can parse.
   *
   * Rahoo
   */
   function subroutine() {
    a = /* inline comment */ b + c ;
   }
   /*/ <-- tricky comments */

   /**
    * Another comment.
    */
    function something() {
    }

```

Extra credit

Ensure that the stripping code is not hard-coded to the particular delimiters described above, but instead allows the caller to specify them.   (If your language supports them,   optional parameters   may be useful for this.)

Other tasks related to string operations:

Metrics

* Array length
* String length
* Copy a string
* Empty string  (assignment)

Counting

* Word frequency
* Letter frequency
* Jewels and stones
* I before E except after C
* Bioinformatics/base count
* Count occurrences of a substring
* Count how many vowels and consonants occur in a string

Remove/replace

* XXXX redacted
* Conjugate a Latin verb
* Remove vowels from a string
* String interpolation (included)
* Strip block comments
* Strip comments from a string
* Strip a set of characters from a string
* Strip whitespace from a string -- top and tail
* Strip control codes and extended characters from a string

Anagrams/Derangements/shuffling

* Word wheel
* ABC problem
* Sattolo cycle
* Knuth shuffle
* Ordered words
* Superpermutation minimisation
* Textonyms (using a phone text pad)
* Anagrams
* Anagrams/Deranged anagrams
* Permutations/Derangements

Find/Search/Determine

* ABC words
* Odd words
* Word ladder
* Semordnilap
* Word search
* Wordiff  (game)
* String matching
* Tea cup rim text
* Alternade words
* Changeable words
* State name puzzle
* String comparison
* Unique characters
* Unique characters in each string
* Extract file extension
* Levenshtein distance
* Palindrome detection
* Common list elements
* Longest common suffix
* Longest common prefix
* Compare a list of strings
* Longest common substring
* Find common directory path
* Words from neighbour ones
* Change e letters to i in words
* Non-continuous subsequences
* Longest common subsequence
* Longest palindromic substrings
* Longest increasing subsequence
* Words containing "the" substring
* Sum of the digits of n is substring of n
* Determine if a string is numeric
* Determine if a string is collapsible
* Determine if a string is squeezable
* Determine if a string has all unique characters
* Determine if a string has all the same characters
* Longest substrings without repeating characters
* Find words which contains all the vowels
* Find words which contain the most consonants
* Find words which contains more than 3 vowels
* Find words whose first and last three letters are equal
* Find words with alternating vowels and consonants

Formatting

* Substring
* Rep-string
* Word wrap
* String case
* Align columns
* Literals/String
* Repeat a string
* Brace expansion
* Brace expansion using ranges
* Reverse a string
* Phrase reversals
* Comma quibbling
* Special characters
* String concatenation
* Substring/Top and tail
* Commatizing numbers
* Reverse words in a string
* Suffixation of decimal numbers
* Long literals, with continuations
* Numerical and alphabetical suffixes
* Abbreviations, easy
* Abbreviations, simple
* Abbreviations, automatic

Song lyrics/poems/Mad Libs/phrases

* Mad Libs
* Magic 8-ball
* 99 bottles of beer
* The Name Game (a song)
* The Old lady swallowed a fly
* The Twelve Days of Christmas

Tokenize

* Text between
* Tokenize a string
* Word break problem
* Tokenize a string with escaping
* Split a character string based on change of character

Sequences

* Show ASCII table
* De Bruijn sequences
* Summarize and say sequence
* Generate lower case ASCII alphabet

[Assistant]
(formerly Perl 6)

```
sample().split(/ '/*' .+? '*/' /).print;

sub sample {
'   /**
    * Some comments
    * longer comments here that we can parse.
    *
    * Rahoo
    */
    function subroutine() {
     a = /* inline comment */ b + c ;
    }
    /*/ <-- tricky comments */

    /**
     * Another comment.
     */
    function something() {
    }
'}

```

Output:

```

    function subroutine() {
     a =  b + c ;
    }

    function something() {
    }

```


[User]
This task has been flagged for clarification. Code on this page in its current state may be flagged incorrect once this task has been clarified. See this page's Talk page for discussion.

The task is to remove text that follow any of a set of comment markers, (in these examples either a hash or a semicolon) from a string or input line.

**Whitespace debacle:**   There is some confusion about whether to remove any whitespace from the input line.

As of 2 September 2011, at least 8 languages (C, C++, Java, Perl, Python, Ruby, sed, UNIX Shell) were incorrect, out of 36 total languages, because they did not trim whitespace by 29 March 2011 rules. Some other languages might be incorrect for the same reason.

**Please discuss this issue at Talk:Strip comments from a string.**

* From 29 March 2011, this task required that: *"The comment marker and any whitespace at the beginning or ends of the resultant line should be removed. A line without comments should be trimmed of any leading or trailing whitespace before being produced as a result."* The task had 28 languages, which did not all meet this new requirement.
* From 28 March 2011, this task required that: *"Whitespace before the comment marker should be removed."*
* From 30 October 2010, this task did not specify whether or not to remove whitespace.

The following examples will be truncated to either "apples, pears " or "apples, pears".

(This example has flipped between "apples, pears " and "apples, pears" in the past.)

```
apples, pears # and bananas
apples, pears ; and bananas

```

Other tasks related to string operations:

Metrics

* Array length
* String length
* Copy a string
* Empty string  (assignment)

Counting

* Word frequency
* Letter frequency
* Jewels and stones
* I before E except after C
* Bioinformatics/base count
* Count occurrences of a substring
* Count how many vowels and consonants occur in a string

Remove/replace

* XXXX redacted
* Conjugate a Latin verb
* Remove vowels from a string
* String interpolation (included)
* Strip block comments
* Strip comments from a string
* Strip a set of characters from a string
* Strip whitespace from a string -- top and tail
* Strip control codes and extended characters from a string

Anagrams/Derangements/shuffling

* Word wheel
* ABC problem
* Sattolo cycle
* Knuth shuffle
* Ordered words
* Superpermutation minimisation
* Textonyms (using a phone text pad)
* Anagrams
* Anagrams/Deranged anagrams
* Permutations/Derangements

Find/Search/Determine

* ABC words
* Odd words
* Word ladder
* Semordnilap
* Word search
* Wordiff  (game)
* String matching
* Tea cup rim text
* Alternade words
* Changeable words
* State name puzzle
* String comparison
* Unique characters
* Unique characters in each string
* Extract file extension
* Levenshtein distance
* Palindrome detection
* Common list elements
* Longest common suffix
* Longest common prefix
* Compare a list of strings
* Longest common substring
* Find common directory path
* Words from neighbour ones
* Change e letters to i in words
* Non-continuous subsequences
* Longest common subsequence
* Longest palindromic substrings
* Longest increasing subsequence
* Words containing "the" substring
* Sum of the digits of n is substring of n
* Determine if a string is numeric
* Determine if a string is collapsible
* Determine if a string is squeezable
* Determine if a string has all unique characters
* Determine if a string has all the same characters
* Longest substrings without repeating characters
* Find words which contains all the vowels
* Find words which contain the most consonants
* Find words which contains more than 3 vowels
* Find words whose first and last three letters are equal
* Find words with alternating vowels and consonants

Formatting

* Substring
* Rep-string
* Word wrap
* String case
* Align columns
* Literals/String
* Repeat a string
* Brace expansion
* Brace expansion using ranges
* Reverse a string
* Phrase reversals
* Comma quibbling
* Special characters
* String concatenation
* Substring/Top and tail
* Commatizing numbers
* Reverse words in a string
* Suffixation of decimal numbers
* Long literals, with continuations
* Numerical and alphabetical suffixes
* Abbreviations, easy
* Abbreviations, simple
* Abbreviations, automatic

Song lyrics/poems/Mad Libs/phrases

* Mad Libs
* Magic 8-ball
* 99 bottles of beer
* The Name Game (a song)
* The Old lady swallowed a fly
* The Twelve Days of Christmas

Tokenize

* Text between
* Tokenize a string
* Word break problem
* Tokenize a string with escaping
* Split a character string based on change of character

Sequences

* Show ASCII table
* De Bruijn sequences
* Summarize and say sequence
* Generate lower case ASCII alphabet

[Assistant]
(formerly Perl 6)

```
$*IN.slurp.subst(/ \h* <[ # ; ]> \N* /, '', :g).print

```


[User]
Task

Strip control codes and extended characters from a string.

The solution should demonstrate how to achieve each of the following results:

:   * a string with control codes stripped (but extended characters not stripped)
    * a string with control codes and extended characters stripped

In ASCII, the control codes have decimal codes 0 through to 31 and 127.

On an ASCII based system, if the control codes are stripped, the resultant string would have all of its characters within the range of 32 to 126 decimal on the ASCII table.

On a non-ASCII based system, we consider characters that do not have a corresponding glyph on the ASCII table (within the ASCII range of 32 to 126 decimal) to be an extended character for the purpose of this task.

Other tasks related to string operations:

Metrics

* Array length
* String length
* Copy a string
* Empty string  (assignment)

Counting

* Word frequency
* Letter frequency
* Jewels and stones
* I before E except after C
* Bioinformatics/base count
* Count occurrences of a substring
* Count how many vowels and consonants occur in a string

Remove/replace

* XXXX redacted
* Conjugate a Latin verb
* Remove vowels from a string
* String interpolation (included)
* Strip block comments
* Strip comments from a string
* Strip a set of characters from a string
* Strip whitespace from a string -- top and tail
* Strip control codes and extended characters from a string

Anagrams/Derangements/shuffling

* Word wheel
* ABC problem
* Sattolo cycle
* Knuth shuffle
* Ordered words
* Superpermutation minimisation
* Textonyms (using a phone text pad)
* Anagrams
* Anagrams/Deranged anagrams
* Permutations/Derangements

Find/Search/Determine

* ABC words
* Odd words
* Word ladder
* Semordnilap
* Word search
* Wordiff  (game)
* String matching
* Tea cup rim text
* Alternade words
* Changeable words
* State name puzzle
* String comparison
* Unique characters
* Unique characters in each string
* Extract file extension
* Levenshtein distance
* Palindrome detection
* Common list elements
* Longest common suffix
* Longest common prefix
* Compare a list of strings
* Longest common substring
* Find common directory path
* Words from neighbour ones
* Change e letters to i in words
* Non-continuous subsequences
* Longest common subsequence
* Longest palindromic substrings
* Longest increasing subsequence
* Words containing "the" substring
* Sum of the digits of n is substring of n
* Determine if a string is numeric
* Determine if a string is collapsible
* Determine if a string is squeezable
* Determine if a string has all unique characters
* Determine if a string has all the same characters
* Longest substrings without repeating characters
* Find words which contains all the vowels
* Find words which contain the most consonants
* Find words which contains more than 3 vowels
* Find words whose first and last three letters are equal
* Find words with alternating vowels and consonants

Formatting

* Substring
* Rep-string
* Word wrap
* String case
* Align columns
* Literals/String
* Repeat a string
* Brace expansion
* Brace expansion using ranges
* Reverse a string
* Phrase reversals
* Comma quibbling
* Special characters
* String concatenation
* Substring/Top and tail
* Commatizing numbers
* Reverse words in a string
* Suffixation of decimal numbers
* Long literals, with continuations
* Numerical and alphabetical suffixes
* Abbreviations, easy
* Abbreviations, simple
* Abbreviations, automatic

Song lyrics/poems/Mad Libs/phrases

* Mad Libs
* Magic 8-ball
* 99 bottles of beer
* The Name Game (a song)
* The Old lady swallowed a fly
* The Twelve Days of Christmas

Tokenize

* Text between
* Tokenize a string
* Word break problem
* Tokenize a string with escaping
* Split a character string based on change of character

Sequences

* Show ASCII table
* De Bruijn sequences
* Summarize and say sequence
* Generate lower case ASCII alphabet

[Assistant]
(formerly Perl 6)

**Works with**: Rakudo version 2018.03

```
my $str = (0..400).roll(80)».chr.join;

say $str;
say $str.subst(/<:Cc>/,      '', :g); # unicode property: control character
say $str.subst(/<-[\ ..~]>/, '', :g);

```

```
kşaNĹĭŗ�|Ęw���"ÄlĄWł8iCƁę��Ż�¬�5ĎĶ'óü¸'ÍŸ;ŢƐ¦�´ŷQċűÒŴ$ÃŅ�Đįð+=ĥƂ+Ōĭħ¼ŕc¤H~ìïēÕ
kşaNĹĭŗ|Ęw"ÄlĄWł8iCƁęŻ¬5ĎĶ'óü¸'ÍŸ;ŢƐ¦´ŷQċűÒŴ$ÃŅĐįð+=ĥƂ+Ōĭħ¼ŕc¤H~ìïēÕ
kaN|w"lW8iC5'';Q$+=+cH~
```


[User]
Task

Demonstrate how to strip leading and trailing whitespace from a string.

The solution should demonstrate how to achieve the following three results:

* String with leading whitespace removed
* String with trailing whitespace removed
* String with both leading and trailing whitespace removed

For the purposes of this task whitespace includes non printable characters such as the space character, the tab character, and other such characters that have no corresponding graphical representation.

Other tasks related to string operations:

Metrics

* Array length
* String length
* Copy a string
* Empty string  (assignment)

Counting

* Word frequency
* Letter frequency
* Jewels and stones
* I before E except after C
* Bioinformatics/base count
* Count occurrences of a substring
* Count how many vowels and consonants occur in a string

Remove/replace

* XXXX redacted
* Conjugate a Latin verb
* Remove vowels from a string
* String interpolation (included)
* Strip block comments
* Strip comments from a string
* Strip a set of characters from a string
* Strip whitespace from a string -- top and tail
* Strip control codes and extended characters from a string

Anagrams/Derangements/shuffling

* Word wheel
* ABC problem
* Sattolo cycle
* Knuth shuffle
* Ordered words
* Superpermutation minimisation
* Textonyms (using a phone text pad)
* Anagrams
* Anagrams/Deranged anagrams
* Permutations/Derangements

Find/Search/Determine

* ABC words
* Odd words
* Word ladder
* Semordnilap
* Word search
* Wordiff  (game)
* String matching
* Tea cup rim text
* Alternade words
* Changeable words
* State name puzzle
* String comparison
* Unique characters
* Unique characters in each string
* Extract file extension
* Levenshtein distance
* Palindrome detection
* Common list elements
* Longest common suffix
* Longest common prefix
* Compare a list of strings
* Longest common substring
* Find common directory path
* Words from neighbour ones
* Change e letters to i in words
* Non-continuous subsequences
* Longest common subsequence
* Longest palindromic substrings
* Longest increasing subsequence
* Words containing "the" substring
* Sum of the digits of n is substring of n
* Determine if a string is numeric
* Determine if a string is collapsible
* Determine if a string is squeezable
* Determine if a string has all unique characters
* Determine if a string has all the same characters
* Longest substrings without repeating characters
* Find words which contains all the vowels
* Find words which contain the most consonants
* Find words which contains more than 3 vowels
* Find words whose first and last three letters are equal
* Find words with alternating vowels and consonants

Formatting

* Substring
* Rep-string
* Word wrap
* String case
* Align columns
* Literals/String
* Repeat a string
* Brace expansion
* Brace expansion using ranges
* Reverse a string
* Phrase reversals
* Comma quibbling
* Special characters
* String concatenation
* Substring/Top and tail
* Commatizing numbers
* Reverse words in a string
* Suffixation of decimal numbers
* Long literals, with continuations
* Numerical and alphabetical suffixes
* Abbreviations, easy
* Abbreviations, simple
* Abbreviations, automatic

Song lyrics/poems/Mad Libs/phrases

* Mad Libs
* Magic 8-ball
* 99 bottles of beer
* The Name Game (a song)
* The Old lady swallowed a fly
* The Twelve Days of Christmas

Tokenize

* Text between
* Tokenize a string
* Word break problem
* Tokenize a string with escaping
* Split a character string based on change of character

Sequences

* Show ASCII table
* De Bruijn sequences
* Summarize and say sequence
* Generate lower case ASCII alphabet

[Assistant]
(formerly Perl 6)

**Works with**: Rakudo version 2020.08.1

```
my $s = "\r\n \t\x2029 Good Stuff \x202F\n";
say $s.trim;
say $s.trim.raku;
say $s.trim-leading.raku;
say $s.trim-trailing.raku;

```

Output:

```
Good Stuff
"Good Stuff"
"Good Stuff  \n"
"\r\n \t
 Good Stuff"

```


[User]
Definitions   (as per number theory)
:   :   * The   **prime(*p*)**   is the    ***p*th   prime.**

        :   :   :   * **prime(1)**   is   **2**
                    * **prime(4)**   is   **7**

        * A    **strong   prime**   is when     **prime(*p*)**   is   **>**   **[prime(*p*-1) + prime(*p*+1)] ÷ 2**
        * A   **weak    prime**   is when     **prime(*p*)**   is   **<**   **[prime(*p*-1) + prime(*p*+1)] ÷ 2**

Note that the definition for   **strong primes**   is different when used in the context of   cryptography.

Task
:   :   * Find and display (on one line) the first   **36**   strong primes.
        * Find and display the   *count*   of the strong primes below   1,000,000.
        * Find and display the   *count*   of the strong primes below 10,000,000.
        * Find and display (on one line) the first   **37**   weak primes.
        * Find and display the   *count*   of the weak primes below   1,000,000.
        * Find and display the   *count*   of the weak primes below 10,000,000.
        * (Optional)   display the   *counts*   and   "below numbers"   with commas.

Show all output here.

Related Task
:   :   * Safe primes and unsafe primes.

Also see
:   :   * The OEIS article A051634: strong primes.
        * The OEIS article A051635: weak primes.

[Assistant]
(formerly Perl 6)

**Works with**: Rakudo version 2018.11

```
sub comma { $^i.flip.comb(3).join(',').flip }

use Math::Primesieve;

my $sieve = Math::Primesieve.new;

my @primes = $sieve.primes(10_000_019);

my (@weak, @balanced, @strong);

for 1 ..^ @primes - 1 -> $p {
    given (@primes[$p - 1] + @primes[$p + 1]) / 2 {
        when * > @primes[$p] {     @weak.push: @primes[$p] }
        when * < @primes[$p] {   @strong.push: @primes[$p] }
        default              { @balanced.push: @primes[$p] }
    }
}

for @strong,   'strong',   36,
    @weak,     'weak',     37,
    @balanced, 'balanced', 28
  -> @pr, $type, $d {
    say "\nFirst $d $type primes:\n", @pr[^$d]».,
    say "Count of $type primes <=  {comma 1e6}:  ", comma +@pr[^(@pr.first: * > 1e6,:k)];
    say "Count of $type primes <= {comma 1e7}: ", comma +@pr;
}

```

Output:

```
First 36 strong primes:
(11 17 29 37 41 59 67 71 79 97 101 107 127 137 149 163 179 191 197 223 227 239 251 269 277 281 307 311 331 347 367 379 397 419 431 439)
Count of strong primes <=  1,000,000:  37,723
Count of strong primes <= 10,000,000: 320,991

First 37 weak primes:
(3 7 13 19 23 31 43 47 61 73 83 89 103 109 113 131 139 151 167 181 193 199 229 233 241 271 283 293 313 317 337 349 353 359 383 389 401)
Count of weak primes <=  1,000,000:  37,780
Count of weak primes <= 10,000,000: 321,750

First 28 balanced primes:
(5 53 157 173 211 257 263 373 563 593 607 653 733 947 977 1,103 1,123 1,187 1,223 1,367 1,511 1,747 1,753 1,907 2,287 2,417 2,677 2,903)
Count of balanced primes <=  1,000,000:  2,994
Count of balanced primes <= 10,000,000: 21,837
```


[User]
A Sturmian word is a binary sequence, finite or infinite, that makes up the cutting sequence for a positive real number x, as shown in the picture.

Example Sturmian word when x = 0.618..., the golden ratio.

The Sturmian word can be computed thus as an algorithm:

* If

  x
  >
  1
  {\displaystyle {\displaystyle x>1}}
  , then it is the inverse of the Sturmian word for

  1

  /
  x
  {\displaystyle {\displaystyle 1/x}}
  . So we have reduced to the case of

  0
  <
  x
  ≤
  1
  {\displaystyle {\displaystyle 0<x\leq 1}}
  .
* Iterate over

  f
  l
  o
  o
  r
  (
  1
  x
  )
  ,
  f
  l
  o
  o
  r
  (
  2
  x
  )
  ,
  f
  l
  o
  o
  r
  (
  3
  x
  )
  ,
  …
  {\displaystyle {\displaystyle floor(1x),floor(2x),floor(3x),\dots }}
* If

  k
  x
  {\displaystyle {\displaystyle kx}}
   is an integer, then the program terminates. Else, if

  f
  l
  o
  o
  r
  (
  (
  k
  −
  1
  )
  x
  )
  =
  f
  l
  o
  o
  r
  (
  k
  x
  )
  {\displaystyle {\displaystyle floor((k-1)x)=floor(kx)}}
  , then the program outputs 0, else, it outputs 10.

The problem:

* Given a positive rational number

  m
  n
  {\displaystyle {\displaystyle {\frac {m}{n}}}}
  , specified by two positive integers

  m
  ,
  n
  {\displaystyle {\displaystyle m,n}}
  , output its entire Sturmian word.
* Given a quadratic real number

  b

  a
  +
  m
  n
  >
  0
  {\displaystyle {\displaystyle {\frac {b{\sqrt {a}}+m}{n}}>0}}
  , specified by integers

  a
  ,
  b
  ,
  m
  ,
  n
  {\displaystyle {\displaystyle a,b,m,n}}
  , where

  a
  {\displaystyle {\displaystyle a}}
   is not a perfect square, output the first

  k
  {\displaystyle {\displaystyle k}}
   letters of Sturmian words when given a positive number

  k
  {\displaystyle {\displaystyle k}}
  .

(If the programming language can represent infinite data structures, then that works too.)

A simple check is to do this for the inverse golden ratio

5
−
1
2
{\displaystyle {\displaystyle {\frac {{\sqrt {5}}-1}{2}}}}
, that is,

a
=
5
,
b
=
1
,
m
=
−
1
,
n
=
2
{\displaystyle {\displaystyle a=5,b=1,m=-1,n=2}}
, which would just output the Fibonacci word.

Stretch goal: calculate the Sturmian word for other kinds of definable real numbers, such as cubic roots.

The key difficulty is accurately calculating

f
l
o
o
r
(
k

a
)
{\displaystyle {\displaystyle floor(k{\sqrt {a}})}}
 for large

k
{\displaystyle {\displaystyle k}}
. Floating point arithmetic would lose precision. One can either do this simply by directly searching for some integer

a
′
{\displaystyle {\displaystyle a'}}
 such that

a

′

2
≤

k

2
a
<
(

a
′
+
1

)

2
{\displaystyle {\displaystyle a'^{2}\leq k^{2}a<(a'+1)^{2}}}
, or by more trickly methods, such as the continued fraction approach.

First calculate the continued fraction convergents to

a
{\displaystyle {\displaystyle {\sqrt {a}}}}
. Let

m
n
{\displaystyle {\displaystyle {\frac {m}{n}}}}
 be a convergent to

a
{\displaystyle {\displaystyle {\sqrt {a}}}}
, such that

n
≥
k
{\displaystyle {\displaystyle n\geq k}}
, then since the convergent sequence is the **best rational approximant** for denominators up to that point, we know for sure that, if we write out

0
k
,

1
k
,
…
{\displaystyle {\displaystyle {\frac {0}{k}},{\frac {1}{k}},\dots }}
, the sequence would stride right across the gap

(
m

/
n
,
2
x
−
m

/
n
)
{\displaystyle {\displaystyle (m/n,2x-m/n)}}
. Thus, we can take the largest

l
{\displaystyle {\displaystyle l}}
 such that

l

/
k
≤
m

/
n
{\displaystyle {\displaystyle l/k\leq m/n}}
, and we would know for sure that

l
=
f
l
o
o
r
(
k

a
)
{\displaystyle {\displaystyle l=floor(k{\sqrt {a}})}}
.

In summary,

f
l
o
o
r
(
k

a
)
=
f
l
o
o
r
(
m
k

/
n
)
{\displaystyle {\displaystyle floor(k{\sqrt {a}})=floor(mk/n)}}
 where

m

/
n
{\displaystyle {\displaystyle m/n}}
 is the first continued fraction approximant to

a
{\displaystyle {\displaystyle {\sqrt {a}}}}
 with a denominator

n
≥
k
{\displaystyle {\displaystyle n\geq k}}

[Assistant]
**Translation of**: Julia

```
# 20240215 Raku programming solution

sub chenfoxlyndonfactorization(Str $s) {
 sub sturmian-word($m, $n) {
   return sturmian-word($n, $m).trans('0' => '1', '1' => '0') if $m > $n;
   my ($res, $k, $prev) = '', 1, 0;
   while ($k * $m) % $n > 0 {
      my $curr = ($k * $m) div $n;
      $res ~= $prev == $curr ?? '0' !! '10';
      $prev = $curr;
      $k++;
   }
   return $res;
}

sub fib-word($n) {
   my ($Sn_1, $Sn) = '0', '01';
   for 2..$n { ($Sn, $Sn_1) = ($Sn~$Sn_1, $Sn) }
   return $Sn;
}

my $fib = fib-word(7);
my $sturmian = sturmian-word(13, 21);
say "{$sturmian} <== 13/21" if $fib.substr(0, $sturmian.chars) eq $sturmian;

sub cfck($a, $b, $m, $n, $k) {
   my (@p, @q) := [0, 1], [1, 0];
   my $r = (sqrt($a) * $b + $m) / $n;
   for ^$k {
      my $whole = $r.Int;
      my ($pn, $qn) = $whole * @p[*-1] + @p[*-2], $whole * @q[*-1] + @q[*-2];
      @p.push($pn);
      @q.push($qn);
      $r = 1/($r - $whole);
   }
   return [@p[*-1], @q[*-1]];
}

my $cfck-result = cfck(5, 1, -1, 2, 8);
say "{sturmian-word($cfck-result[0], $cfck-result[1])} <== 1/phi (8th convergent golden ratio)";

```

Output:

Same as Julia example.

You may Attempt This Online!


[User]
A sub-unit square is a square number (product of two identical non-negative integers) that remains a square after having a 1 subtracted from each digit in the square.

E.G.

The number **1** is a sub-unit square. **1** - **1** is **0**, which is also a square, though it's kind-of a degenerate case.

The number **3136** is a sub-unit square. **3136** (**56²**) with unit **1** subtracted from each digit is **2025** (**45²**).

A sub-unit square cannot contain a digit zero (**0**) since zero minus one is negative one. Every known sub-unit square, with the exception of **1**, ends with the digits **36**.

Task

* Find and display at least the first five sub-unit squares.

See also

* OEIS:A061844 - Squares that remain squares if you decrease every digit by 1

[Assistant]
First seven take about 5 seconds with this implementation. The eighth would take several hours at least.

```
my @upper = 1,|(1 .. *).map((* × 2)²);
my @lower = (^∞).map: *²;
my \R = [\+] 0, 1, 10, 100 … *;

my $l = 0;

.say for (gather {
    (^∞).map: -> $u {
        next if @upper[$u].contains: 0;
        my $chars = @upper[$u].chars;
        loop {
            $l++ and next   if @upper[$u] - @lower[$l]  > R[$chars];
            take @upper[$u] if @upper[$u] - @lower[$l] == R[$chars];
            last;
        }
    }
})[^7]

```

Output:

```
1
36
3136
24336
5973136
71526293136
318723477136
```


[User]
Subleq is an example of a One-Instruction Set Computer (OISC).

It is named after its only instruction, which is **SU**btract and **B**ranch if **L**ess than or **EQ**ual to zero.

Task

Your task is to create an interpreter which emulates a SUBLEQ machine.

The machine's memory consists of an array of signed integers.   These integers may be interpreted in three ways:

:   :   :   :   * simple numeric values
                * memory addresses
                * characters for input or output

Any reasonable word size that accommodates all three of the above uses is fine.

The program should load the initial contents of the emulated machine's memory, set the instruction pointer to the first address (which is defined to be address 0), and begin emulating the machine, which works as follows:

:   1. Let **A** be the value in the memory location identified by the instruction pointer;   let **B** and **C** be the values stored in the next two consecutive addresses in memory.
    2. Advance the instruction pointer three words, to point at the address *after* the address containing **C**.
    3. If **A** is **-1** (negative unity), then a character is read from the machine's input and its numeric value stored in the address given by **B**. **C** is unused. (Most implementations adopt the C convention of signaling EOF by storing -1 as the read-in character.)
    4. If **B** is **-1** (negative unity), then the number contained in the address given by **A** is interpreted as a character and written to the machine's output. **C** is unused.
    5. Otherwise, both **A** and **B** are treated as addresses. The number contained in address **A** is subtracted from the number in address **B** (and the difference left in address **B**). If the result is positive, execution continues uninterrupted; if the result is zero or negative, the instruction pointer is set to **C**.
    6. If the instruction pointer becomes negative, execution halts.

Your solution may initialize the emulated machine's memory in any convenient manner, but if you accept it as input, it should be a separate input stream from the one fed to the emulated machine once it is running. And if fed as text input, it should be in the form of raw subleq "machine code" - whitespace-separated decimal numbers, with no symbolic names or other assembly-level extensions, to be loaded into memory starting at address   **0**   (zero).

For purposes of this task, show the output of your solution when fed the below   "Hello, world!"   program.

As written, this example assumes ASCII or a superset of it, such as any of the Latin-N character sets or Unicode;   you may translate the numbers representing characters (starting with 72=ASCII 'H') into another character set if your implementation runs in a non-ASCII-compatible environment. If 0 is not an appropriate terminator in your character set, the program logic will need some adjustment as well.

```
15 17 -1 17 -1 -1 16 1 -1 16 3 -1 15 15 0 0 -1 72 101 108 108 111 44 32 119 111 114 108 100 33 10 0
```

The above "machine code" corresponds to something like this in a hypothetical assembler language for a signed 8-bit version of the machine:

```
start:
    0f 11 ff subleq (zero), (message), -1 ; subtract 0 from next character value to print;
                                          ; terminate if it's <=0
    11 ff ff subleq (message), -1, -1     ; output character
    10 01 ff subleq (neg1), (start+1), -1 ; modify above two instructions by subtracting -1
    10 03 ff subleq (neg1), (start+3), -1 ;   (adding 1) to their target addresses
    0f 0f 00 subleq (zero), (zero), start ; if 0-0 <= 0 (i.e. always) goto start

; useful constants
zero:
    00      .data 0
neg1:
    ff      .data -1
; the message to print
message: .data "Hello, world!\n\0"
    48 65 6c 6c 6f 2c 20 77 6f 72 6c 64 21 0a 00
```

[Assistant]
(formerly Perl 6)

**Translation of**: Perl

```
my @hello-world =
|<15 17 -1 17 -1 -1 16 1 -1 16 3 -1 15 15 0 0 -1>,
|"Hello, world!\n\0".comb.map(*.ord);

sub run-subleq(@memory) {
  my $ip = 0;
  while $ip >= 0 && $ip < @memory {
    my ($a, $b, $c) = @memory[$ip..*];
    $ip += 3;
    if $a < 0 {
      @memory[$b] = getc.ord;
    } elsif $b < 0 {
      print @memory[$a].chr;
    } else {
      if (@memory[$b] -= @memory[$a]) <= 0 {
        $ip = $c;
      }
    }
  }
}

run-subleq @hello-world;

```

Output:

```
Hello, world!
```


[User]
Task

Implement a function/procedure/method/subroutine that takes a set/array/list/stream/table/collection of words with integer weights, and identifies a non-empty subset of them whose weights sum to zero (cf. the Dropbox Diet candidate screening exercise and the Subset sum problem Wikipedia article).

For example

This set of weighted words, one solution would be the set of words:

:   :   :   * {elysee,   efferent,   deploy,   departure,   centipede,   bonnet,   balm,   archbishop}

because their respective weights of:

:   :   :   * -326,   54,   44,   952,   -658,   452,   397,   and   -915

sum to zero.

:   :   :   :   :   :   Table of weighted words

                        | word | weight |
                        | --- | --- |
                        | alliance | -624 |
                        | archbishop | -915 |
                        | balm | 397 |
                        | bonnet | 452 |
                        | brute | 870 |
                        | centipede | -658 |
                        | cobol | 362 |
                        | covariate | 590 |
                        | departure | 952 |
                        | deploy | 44 |
                        | diophantine | 645 |
                        | efferent | 54 |
                        | elysee | -326 |
                        | eradicate | 376 |
                        | escritoire | 856 |
                        | exorcism | -983 |
                        | fiat | 170 |
                        | filmy | -874 |
                        | flatworm | 503 |
                        | gestapo | 915 |
                        | infra | -847 |
                        | isis | -982 |
                        | lindholm | 999 |
                        | markham | 475 |
                        | mincemeat | -880 |
                        | moresby | 756 |
                        | mycenae | 183 |
                        | plugging | -266 |
                        | smokescreen | 423 |
                        | speakeasy | -745 |
                        | vein | 813 |

Another solution would be the set of words {flatworm, gestapo, infra, isis, lindholm, plugging, smokescreen, speakeasy}, because their respective weights of 503, 915, -847, -982, 999, -266, 423, and -745 also sum to zero.

You may assume the weights range from -1000 to 1000.

If there are multiple solutions, only one needs to be found.

Use any algorithm you want and demonstrate it on a set of at least 30 weighted words with the results shown in a human readable form.

Note that an implementation that depends on enumerating all possible subsets is likely to be infeasible.

[Assistant]
(formerly Perl 6)

```
my @pairs =
    alliance => -624, archbishop => -915, balm => 397, bonnet => 452,
    brute => 870, centipede => -658, cobol => 362, covariate => 590,
    departure => 952, deploy => 44, diophantine => 645, efferent => 54,
    elysee => -326, eradicate => 376, escritoire => 856, exorcism => -983,
    fiat => 170, filmy => -874, flatworm => 503, gestapo => 915,
    infra => -847, isis => -982, lindholm => 999, markham => 475,
    mincemeat => -880, moresby => 756, mycenae => 183, plugging => -266,
    smokescreen => 423, speakeasy => -745, vein => 813;
my @weights = @pairs».value;
my %name = @pairs.hash.invert;

.say for (1..27).hyper(:3batch).map: -> $n {
    given @weights.combinations($n).first({ 0 == [+] @^comb }) {
        when .so { "Length $n: ({.map: {%name{$_}}})" }
        default  { "Length $n: (none)" }
    }
}

```

Output:

```
Length 1: (none)
Length 2: (archbishop gestapo)
Length 3: (centipede markham mycenae)
Length 4: (alliance balm deploy mycenae)
Length 5: (alliance brute covariate deploy mincemeat)
Length 6: (alliance archbishop balm deploy gestapo mycenae)
Length 7: (alliance archbishop bonnet cobol departure exorcism moresby)
Length 8: (alliance archbishop balm bonnet fiat flatworm isis lindholm)
Length 9: (alliance archbishop balm bonnet brute covariate eradicate mincemeat plugging)
Length 10: (alliance archbishop balm bonnet brute centipede cobol departure deploy mincemeat)
Length 11: (alliance archbishop balm bonnet brute centipede cobol departure infra moresby speakeasy)
Length 12: (alliance archbishop balm bonnet brute centipede cobol covariate diophantine efferent elysee infra)
Length 13: (alliance archbishop balm bonnet brute centipede cobol covariate departure efferent eradicate filmy isis)
Length 14: (alliance archbishop balm bonnet brute centipede cobol covariate departure deploy elysee filmy markham speakeasy)
Length 15: (alliance archbishop balm bonnet brute centipede cobol covariate departure deploy elysee exorcism flatworm infra mycenae)
Length 16: (alliance archbishop balm bonnet brute centipede cobol covariate departure deploy diophantine elysee exorcism filmy gestapo infra)
Length 17: (alliance archbishop balm bonnet brute centipede cobol covariate departure deploy diophantine exorcism isis mincemeat mycenae plugging vein)
Length 18: (alliance archbishop balm bonnet brute centipede cobol covariate departure deploy diophantine efferent elysee exorcism filmy isis mycenae vein)
Length 19: (alliance archbishop balm bonnet brute centipede cobol covariate departure deploy diophantine efferent elysee eradicate exorcism fiat infra isis smokescreen)
Length 20: (alliance archbishop balm bonnet brute centipede cobol covariate departure deploy diophantine efferent elysee eradicate exorcism gestapo infra isis smokescreen speakeasy)
Length 21: (alliance archbishop balm bonnet brute centipede cobol covariate departure deploy diophantine efferent elysee eradicate exorcism flatworm infra lindholm mincemeat plugging speakeasy)
Length 22: (alliance archbishop balm bonnet brute centipede cobol covariate departure deploy diophantine efferent elysee eradicate escritoire exorcism fiat filmy flatworm mincemeat plugging speakeasy)
Length 23: (alliance archbishop balm bonnet brute centipede cobol covariate departure deploy diophantine efferent elysee eradicate escritoire exorcism infra isis mincemeat moresby mycenae smokescreen speakeasy)
Length 24: (alliance archbishop balm bonnet brute centipede cobol covariate departure deploy diophantine efferent elysee exorcism filmy gestapo infra markham mincemeat moresby mycenae plugging smokescreen speakeasy)
Length 25: (alliance archbishop balm bonnet brute centipede cobol covariate departure deploy diophantine eradicate exorcism fiat filmy flatworm infra isis lindholm markham mincemeat moresby mycenae plugging speakeasy)
Length 26: (alliance archbishop balm bonnet brute centipede cobol covariate departure deploy diophantine elysee eradicate escritoire exorcism fiat filmy gestapo infra isis markham mincemeat mycenae plugging speakeasy vein)
Length 27: (alliance archbishop balm bonnet brute centipede covariate departure deploy efferent elysee eradicate escritoire exorcism fiat filmy flatworm infra isis lindholm markham mincemeat moresby mycenae plugging smokescreen speakeasy)
```


[User]
Substitution Cipher Implementation - File Encryption/Decryption

Task

Encrypt an input/source file by replacing every upper/lower case alphabets of the source file with another predetermined upper/lower case alphabets or symbols and save it into another output/encrypted file and then again convert that output/encrypted file into original/decrypted file.

This type of Encryption/Decryption scheme is often called a Substitution Cipher.

Related tasks

* Caesar cipher
* Rot-13
* Vigenère Cipher/Cryptanalysis

See also

* Wikipedia: Substitution cipher

[Assistant]
(formerly Perl 6)

**Works with**: Rakudo version 2015-11-20

Feed it an action (encode, decode) and a file name at the command line and it will spit out the (en|de)coded file to STDOUT. Redirect into a file to save it. If no parameters are passed in, does the demo encode/decode.

```
my $chr = (' ' .. '}').join('');
my $key = $chr.comb.pick(*).join('');

# Be very boring and use the same key every time to fit task reqs.
$key = q☃3#}^",dLs*>tPMcZR!fmC rEKhlw1v4AOgj7Q]YI+|pDB82a&XFV9yzuH<WT%N;iS.0e:`G\n['6@_{bk)=-5qx(/?$JoU☃;

sub MAIN ($action = 'encode', $file = '') {

    die 'Only options are encode or decode.' unless $action ~~ any 'encode'|'decode';

    my $text = qq:to/END/;
        Here we have to do is there will be a input/source file in which
        we are going to Encrypt the file by replacing every upper/lower
        case alphabets of the source file with another predetermined
        upper/lower case alphabets or symbols and save it into another
        output/encrypted file and then again convert that output/encrypted
        file into original/decrypted file. This type of Encryption/Decryption
        scheme is often called a Substitution Cipher.
        END

    $text = $file.IO.slurp if $file;

    say "Key = $key\n";

    if $file {
        say &::($action)($text);
    } else {
        my $encoded;
        say "Encoded text: \n {$encoded = encode $text}";
        say "Decoded text: \n {decode $encoded}";
    }
}

sub encode ($text) { $text.trans($chr => $key) }

sub decode ($text) { $text.trans($key => $chr) }

```

Output:

with no passed parameters

```
Key = 3#}^",dLs*>tPMcZR!fmC rEKhlw1v4AOgj7Q]YI+|pDB82a&XFV9yzuH<WT%N;iS.0e:`G\n['6@_{bk)=-5qx(/?$JoU

Encoded text:
 +`=`3(`3n.x`35b3:b3[-35n`=`3([@@30`3.3[{kq5Z-bq=e`3G[@`3[{3(n[en3
(`3.=`3\b[{\35b3]{e=?k535n`3G[@`30?3=`k@.e[{\3`x`=?3qkk`=Z@b(`=3
e.-`3.@kn.0`5-3bG35n`3-bq=e`3G[@`3([5n3.{b5n`=3k=`:`5`=_[{`:3
qkk`=Z@b(`=3e.-`3.@kn.0`5-3b=3-?_0b@-3.{:3-.x`3[53[{5b3.{b5n`=3
bq5kq5Z`{e=?k5`:3G[@`3.{:35n`{3.\.[{3eb{x`=535n.53bq5kq5Z`{e=?k5`:3
G[@`3[{5b3b=[\[{.@Z:`e=?k5`:3G[@`c39n[-35?k`3bG3]{e=?k5[b{ZQ`e=?k5[b{
-en`_`3[-3bG5`{3e.@@`:3.3Vq0-5[5q5[b{37[kn`=c

Decoded text:
 Here we have to do is there will be a input/source file in which
we are going to Encrypt the file by replacing every upper/lower
case alphabets of the source file with another predetermined
upper/lower case alphabets or symbols and save it into another
output/encrypted file and then again convert that output/encrypted
file into original/decrypted file. This type of Encryption/Decryption
scheme is often called a Substitution Cipher.

```


[User]
Task

Display a substring:

:   * starting from   **n**   characters in and of   **m**   length;
    * starting from   **n**   characters in,   up to the end of the string;
    * whole string minus the last character;
    * starting from a known   character   within the string and of   **m**   length;
    * starting from a known   substring   within the string and of   **m**   length.

If the program uses UTF-8 or UTF-16,   it must work on any valid Unicode code point,
whether in the   Basic Multilingual Plane   or above it.

The program must reference logical characters (code points),   not 8-bit code units for UTF-8 or 16-bit code units for UTF-16.

Programs for other encodings (such as 8-bit ASCII, or EUC-JP) are not required to handle all Unicode characters.

Other tasks related to string operations:

Metrics

* Array length
* String length
* Copy a string
* Empty string  (assignment)

Counting

* Word frequency
* Letter frequency
* Jewels and stones
* I before E except after C
* Bioinformatics/base count
* Count occurrences of a substring
* Count how many vowels and consonants occur in a string

Remove/replace

* XXXX redacted
* Conjugate a Latin verb
* Remove vowels from a string
* String interpolation (included)
* Strip block comments
* Strip comments from a string
* Strip a set of characters from a string
* Strip whitespace from a string -- top and tail
* Strip control codes and extended characters from a string

Anagrams/Derangements/shuffling

* Word wheel
* ABC problem
* Sattolo cycle
* Knuth shuffle
* Ordered words
* Superpermutation minimisation
* Textonyms (using a phone text pad)
* Anagrams
* Anagrams/Deranged anagrams
* Permutations/Derangements

Find/Search/Determine

* ABC words
* Odd words
* Word ladder
* Semordnilap
* Word search
* Wordiff  (game)
* String matching
* Tea cup rim text
* Alternade words
* Changeable words
* State name puzzle
* String comparison
* Unique characters
* Unique characters in each string
* Extract file extension
* Levenshtein distance
* Palindrome detection
* Common list elements
* Longest common suffix
* Longest common prefix
* Compare a list of strings
* Longest common substring
* Find common directory path
* Words from neighbour ones
* Change e letters to i in words
* Non-continuous subsequences
* Longest common subsequence
* Longest palindromic substrings
* Longest increasing subsequence
* Words containing "the" substring
* Sum of the digits of n is substring of n
* Determine if a string is numeric
* Determine if a string is collapsible
* Determine if a string is squeezable
* Determine if a string has all unique characters
* Determine if a string has all the same characters
* Longest substrings without repeating characters
* Find words which contains all the vowels
* Find words which contain the most consonants
* Find words which contains more than 3 vowels
* Find words whose first and last three letters are equal
* Find words with alternating vowels and consonants

Formatting

* Substring
* Rep-string
* Word wrap
* String case
* Align columns
* Literals/String
* Repeat a string
* Brace expansion
* Brace expansion using ranges
* Reverse a string
* Phrase reversals
* Comma quibbling
* Special characters
* String concatenation
* Substring/Top and tail
* Commatizing numbers
* Reverse words in a string
* Suffixation of decimal numbers
* Long literals, with continuations
* Numerical and alphabetical suffixes
* Abbreviations, easy
* Abbreviations, simple
* Abbreviations, automatic

Song lyrics/poems/Mad Libs/phrases

* Mad Libs
* Magic 8-ball
* 99 bottles of beer
* The Name Game (a song)
* The Old lady swallowed a fly
* The Twelve Days of Christmas

Tokenize

* Text between
* Tokenize a string
* Word break problem
* Tokenize a string with escaping
* Split a character string based on change of character

Sequences

* Show ASCII table
* De Bruijn sequences
* Summarize and say sequence
* Generate lower case ASCII alphabet

[Assistant]
(formerly Perl 6)

```
my $str = 'abcdefgh';
my $n = 2;
my $m = 3;
say $str.substr($n, $m);
say $str.substr($n);
say $str.substr(0, *-1);
say $str.substr($str.index('d'), $m);
say $str.substr($str.index('de'), $m);
```


[User]
Task

Find all primes in which all substrings (in base ten) are also primes.

This *can* be achieved by filtering all primes below 500 (there are 95 of them), but there *are* better ways.

Advanced

Solve by testing at most 15 numbers for primality. Show a list of all numbers tested that were not prime.

[Assistant]
```
my @p = (^10).grep: *.is-prime;

say gather while @p {
    .take for @p;

    @p = ( @p X~ <3 7> ).grep: { .is-prime and .substr(*-2,2).is-prime }
}

```

Output:

```
(2 3 5 7 23 37 53 73 373)
```

### Stretch Goal

```
my $prime-tests = 0;
my @non-primes;
sub spy-prime ($n) {
    $prime-tests++;
    my $is-p = $n.is-prime;

    push @non-primes, $n unless $is-p;
    return $is-p;
}

my @p = <2 3 5 7>;

say gather while @p {
    .take for @p;

    @p = ( @p X~ <3 7> ).grep: { !.ends-with(33|77) and .&spy-prime };
}
.say for :$prime-tests, :@non-primes;

```

Output:

```
(2 3 5 7 23 37 53 73 373)
prime-tests => 11
non-primes => [27 57 237 537 737 3737]
```


[User]
The task is to demonstrate how to remove the first and last characters from a string.

The solution should demonstrate how to obtain the following results:

* String with first character removed
* String with last character removed
* String with both the first and last characters removed

If the program uses UTF-8 or UTF-16, it must work on any valid Unicode code point, whether in the Basic Multilingual Plane or above it.

The program must reference logical characters (code points), not 8-bit code units for UTF-8 or 16-bit code units for UTF-16.

Programs for other encodings (such as 8-bit ASCII, or EUC-JP) are not required to handle all Unicode characters.

Other tasks related to string operations:

Metrics

* Array length
* String length
* Copy a string
* Empty string  (assignment)

Counting

* Word frequency
* Letter frequency
* Jewels and stones
* I before E except after C
* Bioinformatics/base count
* Count occurrences of a substring
* Count how many vowels and consonants occur in a string

Remove/replace

* XXXX redacted
* Conjugate a Latin verb
* Remove vowels from a string
* String interpolation (included)
* Strip block comments
* Strip comments from a string
* Strip a set of characters from a string
* Strip whitespace from a string -- top and tail
* Strip control codes and extended characters from a string

Anagrams/Derangements/shuffling

* Word wheel
* ABC problem
* Sattolo cycle
* Knuth shuffle
* Ordered words
* Superpermutation minimisation
* Textonyms (using a phone text pad)
* Anagrams
* Anagrams/Deranged anagrams
* Permutations/Derangements

Find/Search/Determine

* ABC words
* Odd words
* Word ladder
* Semordnilap
* Word search
* Wordiff  (game)
* String matching
* Tea cup rim text
* Alternade words
* Changeable words
* State name puzzle
* String comparison
* Unique characters
* Unique characters in each string
* Extract file extension
* Levenshtein distance
* Palindrome detection
* Common list elements
* Longest common suffix
* Longest common prefix
* Compare a list of strings
* Longest common substring
* Find common directory path
* Words from neighbour ones
* Change e letters to i in words
* Non-continuous subsequences
* Longest common subsequence
* Longest palindromic substrings
* Longest increasing subsequence
* Words containing "the" substring
* Sum of the digits of n is substring of n
* Determine if a string is numeric
* Determine if a string is collapsible
* Determine if a string is squeezable
* Determine if a string has all unique characters
* Determine if a string has all the same characters
* Longest substrings without repeating characters
* Find words which contains all the vowels
* Find words which contain the most consonants
* Find words which contains more than 3 vowels
* Find words whose first and last three letters are equal
* Find words with alternating vowels and consonants

Formatting

* Substring
* Rep-string
* Word wrap
* String case
* Align columns
* Literals/String
* Repeat a string
* Brace expansion
* Brace expansion using ranges
* Reverse a string
* Phrase reversals
* Comma quibbling
* Special characters
* String concatenation
* Substring/Top and tail
* Commatizing numbers
* Reverse words in a string
* Suffixation of decimal numbers
* Long literals, with continuations
* Numerical and alphabetical suffixes
* Abbreviations, easy
* Abbreviations, simple
* Abbreviations, automatic

Song lyrics/poems/Mad Libs/phrases

* Mad Libs
* Magic 8-ball
* 99 bottles of beer
* The Name Game (a song)
* The Old lady swallowed a fly
* The Twelve Days of Christmas

Tokenize

* Text between
* Tokenize a string
* Word break problem
* Tokenize a string with escaping
* Split a character string based on change of character

Sequences

* Show ASCII table
* De Bruijn sequences
* Summarize and say sequence
* Generate lower case ASCII alphabet

[Assistant]
(formerly Perl 6)

Raku provides both functional and method forms of substr. Note that, unlike in Perl 5, offsets from the end do not use negative numbers, but instead require a function expressing the negative offset relative to the length parameter, which is supplied by the operator. The form \*-1 is just a simple way to write such a function.

We use musical sharps and flats to illustrate that Raku is comfortable with characters from any Unicode plane.

```
my $s = '𝄪♯♮♭𝄫';

print qq:to/END/;
    Original:
    $s

    Remove first character:
    { substr($s, 1) }
    { $s.substr(1) }

    Remove last character:
    { substr($s, 0, *-1) }
    { $s.substr( 0, *-1) }
    { $s.chop }

    Remove first and last characters:
    { substr($s, 1, *-1) }
    { $s.substr(1, *-1) }
    END

```

Output:

```
Original:
𝄪♯♮♭𝄫

Remove first character:
♯♮♭𝄫
♯♮♭𝄫

Remove last character:
𝄪♯♮♭
𝄪♯♮♭
𝄪♯♮♭

Remove first and last characters:
♯♮♭
♯♮♭
```


[User]
A *subtractive generator* calculates a sequence of random numbers, where each number is congruent to the subtraction of two previous numbers from the sequence.
The formula is

* r

  n
  =

  r

  (
  n
  −
  i
  )
  −

  r

  (
  n
  −
  j
  )

  (
  mod

  m
  )
  {\displaystyle {\displaystyle r\_{n}=r\_{(n-i)}-r\_{(n-j)}{\pmod {m}}}}

for some fixed values of

i
{\displaystyle {\displaystyle i}}
,

j
{\displaystyle {\displaystyle j}}
 and

m
{\displaystyle {\displaystyle m}}
, all positive integers. Supposing that

i
>
j
{\displaystyle {\displaystyle i>j}}
, then the state of this generator is the list of the previous numbers from

r

n
−
i
{\displaystyle {\displaystyle r\_{n-i}}}
 to

r

n
−
1
{\displaystyle {\displaystyle r\_{n-1}}}
. Many states generate uniform random integers from

0
{\displaystyle {\displaystyle 0}}
 to

m
−
1
{\displaystyle {\displaystyle m-1}}
, but some states are bad. A state, filled with zeros, generates only zeros. If

m
{\displaystyle {\displaystyle m}}
 is even, then a state, filled with even numbers, generates only even numbers. More generally, if

f
{\displaystyle {\displaystyle f}}
 is a factor of

m
{\displaystyle {\displaystyle m}}
, then a state, filled with multiples of

f
{\displaystyle {\displaystyle f}}
, generates only multiples of

f
{\displaystyle {\displaystyle f}}
.

All subtractive generators have some weaknesses. The formula correlates

r

n
{\displaystyle {\displaystyle r\_{n}}}
,

r

(
n
−
i
)
{\displaystyle {\displaystyle r\_{(n-i)}}}
 and

r

(
n
−
j
)
{\displaystyle {\displaystyle r\_{(n-j)}}}
; these three numbers are not independent, as true random numbers would be. Anyone who observes

i
{\displaystyle {\displaystyle i}}
 consecutive numbers can predict the next numbers, so the generator is not cryptographically secure. The authors of *Freeciv* (utility/rand.c) and *xpat2* (src/testit2.c) knew another problem: the low bits are less random than the high bits.

The subtractive generator has a better reputation than the linear congruential generator, perhaps because it holds more state. A subtractive generator might never multiply numbers: this helps where multiplication is slow. A subtractive generator might also avoid division: the value of

r

(
n
−
i
)
−

r

(
n
−
j
)
{\displaystyle {\displaystyle r\_{(n-i)}-r\_{(n-j)}}}
 is always between

−
m
{\displaystyle {\displaystyle -m}}
 and

m
{\displaystyle {\displaystyle m}}
, so a program only needs to add

m
{\displaystyle {\displaystyle m}}
 to negative numbers.

The choice of

i
{\displaystyle {\displaystyle i}}
 and

j
{\displaystyle {\displaystyle j}}
 affects the period of the generator. A popular choice is

i
=
55
{\displaystyle {\displaystyle i=55}}
 and

j
=
24
{\displaystyle {\displaystyle j=24}}
, so the formula is

* r

  n
  =

  r

  (
  n
  −
  55
  )
  −

  r

  (
  n
  −
  24
  )

  (
  mod

  m
  )
  {\displaystyle {\displaystyle r\_{n}=r\_{(n-55)}-r\_{(n-24)}{\pmod {m}}}}

The subtractive generator from *xpat2* uses

* r

  n
  =

  r

  (
  n
  −
  55
  )
  −

  r

  (
  n
  −
  24
  )

  (
  mod

  10

  9
  )
  {\displaystyle {\displaystyle r\_{n}=r\_{(n-55)}-r\_{(n-24)}{\pmod {10^{9}}}}}

The implementation is by J. Bentley and comes from program\_tools/universal.c of the DIMACS (netflow) archive at Rutgers University. It credits Knuth, TAOCP, Volume 2, Section 3.2.2 (Algorithm A).

Bentley uses this clever algorithm to seed the generator.

1. Start with a single

   s
   e
   e
   d
   {\displaystyle {\displaystyle seed}}
    in range

   0
   {\displaystyle {\displaystyle 0}}
    to

   10

   9
   −
   1
   {\displaystyle {\displaystyle 10^{9}-1}}
   .
2. Set

   s

   0
   =
   s
   e
   e
   d
   {\displaystyle {\displaystyle s\_{0}=seed}}
    and

   s

   1
   =
   1
   {\displaystyle {\displaystyle s\_{1}=1}}
   . The inclusion of

   s

   1
   =
   1
   {\displaystyle {\displaystyle s\_{1}=1}}
    avoids some bad states (like all zeros, or all multiples of 10).
3. Compute

   s

   2
   ,

   s

   3
   ,
   .
   .
   .
   ,

   s

   54
   {\displaystyle {\displaystyle s\_{2},s\_{3},...,s\_{54}}}
    using the subtractive formula

   s

   n
   =

   s

   (
   n
   −
   2
   )
   −

   s

   (
   n
   −
   1
   )

   (
   mod

   10

   9
   )
   {\displaystyle {\displaystyle s\_{n}=s\_{(n-2)}-s\_{(n-1)}{\pmod {10^{9}}}}}
   .
4. Reorder these 55 values so

   r

   0
   =

   s

   34
   {\displaystyle {\displaystyle r\_{0}=s\_{34}}}
   ,

   r

   1
   =

   s

   13
   {\displaystyle {\displaystyle r\_{1}=s\_{13}}}
   ,

   r

   2
   =

   s

   47
   {\displaystyle {\displaystyle r\_{2}=s\_{47}}}
   , ...,

   r

   n
   =

   s

   (
   34
   ∗
   (
   n
   +
   1
   )

   (
   mod

   55
   )
   )
   {\displaystyle {\displaystyle r\_{n}=s\_{(34\*(n+1){\pmod {55}})}}}
   .
   * This is the same order as

     s

     0
     =

     r

     54
     {\displaystyle {\displaystyle s\_{0}=r\_{54}}}
     ,

     s

     1
     =

     r

     33
     {\displaystyle {\displaystyle s\_{1}=r\_{33}}}
     ,

     s

     2
     =

     r

     12
     {\displaystyle {\displaystyle s\_{2}=r\_{12}}}
     , ...,

     s

     n
     =

     r

     (
     (
     34
     ∗
     n
     )
     −
     1

     (
     mod

     55
     )
     )
     {\displaystyle {\displaystyle s\_{n}=r\_{((34\*n)-1{\pmod {55}})}}}
     .
   * This rearrangement exploits how 34 and 55 are relatively prime.
5. Compute the next 165 values

   r

   55
   {\displaystyle {\displaystyle r\_{55}}}
    to

   r

   219
   {\displaystyle {\displaystyle r\_{219}}}
   . Store the last 55 values.

This generator yields the sequence

r

220
{\displaystyle {\displaystyle r\_{220}}}
,

r

221
{\displaystyle {\displaystyle r\_{221}}}
,

r

222
{\displaystyle {\displaystyle r\_{222}}}
 and so on. For example, if the seed is 292929, then the sequence begins with

r

220
=
467478574
{\displaystyle {\displaystyle r\_{220}=467478574}}
,

r

221
=
512932792
{\displaystyle {\displaystyle r\_{221}=512932792}}
,

r

222
=
539453717
{\displaystyle {\displaystyle r\_{222}=539453717}}
. By starting at

r

220
{\displaystyle {\displaystyle r\_{220}}}
, this generator avoids a bias from the first numbers of the sequence. This generator must store the last 55 numbers of the sequence, so to compute the next

r

n
{\displaystyle {\displaystyle r\_{n}}}
. Any array or list would work; a ring buffer is ideal but not necessary.

Implement a subtractive generator that replicates the sequences from *xpat2*.

[Assistant]
(formerly Perl 6)

**Translation of**: Perl

**Works with**: Rakudo version 2018.03

```
sub bentley-clever($seed) {
    constant $mod = 1_000_000_000;
    my @seeds = ($seed % $mod, 1, (* - *) % $mod ... *)[^55];
    my @state = @seeds[ 34, (* + 34 ) % 55 ... 0 ];

    sub subrand() {
        push @state, (my $x = (@state.shift - @state[*-24]) % $mod);
        $x;
    }

    subrand for 55 .. 219;

    &subrand ... *;
}

my @sr = bentley-clever(292929);
.say for @sr[^10];

```

Here we just make the seeder return the random sequence as a lazy list.

Output:

```
467478574
512932792
539453717
20349702
615542081
378707948
933204586
824858649
506003769
380969305
```


[User]
The series of increasing prime numbers begins: `2, 3, 5, 7, 11, 13, 17, 19, 23, 29, ...`

The task applies a filter to the series returning groups of *successive* primes, (s'primes), that differ from the next by a given value or values.

**Example 1:** Specifying that the difference between s'primes be `2` leads to the groups:

:   `(3, 5), (5, 7), (11, 13), (17, 19), (29, 31), ...`

(Known as Twin primes or Prime pairs)

**Example 2:** Specifying more than one difference *between* s'primes leads to groups of size one greater than the number of differences. Differences of `2, 4` leads to the groups:

:   `(5, 7, 11), (11, 13, 17), (17, 19, 23), (41, 43, 47), ...`.

In the first group 7 is two more than 5 and 11 is four more than 7; as well as 5, 7, and 11 being *successive* primes.
Differences are checked in the order of the values given, (differences of `4, 2` would give different groups entirely).

Task

* In each case use a list of primes less than 1\_000\_000
* For the following Differences show the first and last group, as well as the number of groups found:

:   1. Differences of `2`.
    2. Differences of `1`.
    3. Differences of `2, 2`.
    4. Differences of `2, 4`.
    5. Differences of `4, 2`.
    6. Differences of `6, 4, 2`.

* Show output here.

Note: Generation of a list of primes is a secondary aspect of the task. Use of a built in function, well known library, or importing/use of prime generators from other Rosetta Code tasks is encouraged.

references
:   1. https://pdfs.semanticscholar.org/78a1/7349819304863ae061df88dbcb26b4908f03.pdf
    2. https://www.primepuzzles.net/puzzles/puzz\_011.htm
    3. https://matheplanet.de/matheplanet/nuke/html/viewtopic.php?topic=232720&start=0

[Assistant]
(formerly Perl 6)

### Categorized by Successive

**Works with**: Rakudo version 2019.03

Essentially the code from the Sexy primes task with minor tweaks.

```
use Math::Primesieve;
my $sieve = Math::Primesieve.new;

my $max = 1_000_000;
my @primes = $sieve.primes($max);
my $filter = @primes.Set;
my $primes = @primes.categorize: &successive;

sub successive ($i) {
    gather {
        take '2' if $filter{$i + 2};
        take '1' if $filter{$i + 1};
        take '2_2' if all($filter{$i «+« (2,4)});
        take '2_4' if all($filter{$i «+« (2,6)});
        take '4_2' if all($filter{$i «+« (4,6)});
        take '6_4_2' if all($filter{$i «+« (6,10,12)}) and
            none($filter{$i «+« (2,4,8)});
    }
}

sub comma { $^i.flip.comb(3).join(',').flip }

for (2,), (1,), (2,2), (2,4), (4,2), (6,4,2) -> $succ {
    say "## Sets of {1+$succ} successive primes <= { comma $max } with " ~
        "successive differences of { $succ.join: ', ' }";
    my $i = $succ.join: '_';
    for 'First', 0, ' Last', * - 1 -> $where, $ind {
        say "$where group: ", join ', ', [\+] flat $primes{$i}[$ind], |$succ
    }
    say '      Count: ', +$primes{$i}, "\n";
}

```

Output:

```
## Sets of 2 successive primes <= 1,000,000 with successive differences of 2
First group: 3, 5
 Last group: 999959, 999961
      Count: 8169

## Sets of 2 successive primes <= 1,000,000 with successive differences of 1
First group: 2, 3
 Last group: 2, 3
      Count: 1

## Sets of 3 successive primes <= 1,000,000 with successive differences of 2, 2
First group: 3, 5, 7
 Last group: 3, 5, 7
      Count: 1

## Sets of 3 successive primes <= 1,000,000 with successive differences of 2, 4
First group: 5, 7, 11
 Last group: 999431, 999433, 999437
      Count: 1393

## Sets of 3 successive primes <= 1,000,000 with successive differences of 4, 2
First group: 7, 11, 13
 Last group: 997807, 997811, 997813
      Count: 1444

## Sets of 4 successive primes <= 1,000,000 with successive differences of 6, 4, 2
First group: 31, 37, 41, 43
 Last group: 997141, 997147, 997151, 997153
      Count: 306

```

### Precomputed Differences

**Works with**: Rakudo version 2019.03

```
use Math::Primesieve;

constant $max    = 1_000_000;
constant @primes = Math::Primesieve.primes($max);
constant @diffs  = @primes.skip Z- @primes;

say "Given all ordered primes <= $max, sets with successive differences of:";
for (2,), (1,), (2,2), (2,4), (4,2), (6,4,2) -> @succ {
    my $size = @succ.elems;

    my @group_start_offsets = @diffs.rotor( $size => 1-$size )
                                    .grep(:k, { $_ eqv @succ });

    my ($first, $last) = @group_start_offsets[0, *-1]
                         .map: { @primes.skip($_).head($size + 1) };

    say sprintf '%10s has %5d sets: %15s … %s',
        @succ.gist, @group_start_offsets.elems, $first, $last;
}

```

Output:

```
Given all ordered primes <= 1000000, sets with successive differences of:
       (2) has  8169 sets:             3 5 … 999959 999961
       (1) has     1 sets:             2 3 … 2 3
     (2 2) has     1 sets:           3 5 7 … 3 5 7
     (2 4) has  1393 sets:          5 7 11 … 999431 999433 999437
     (4 2) has  1444 sets:         7 11 13 … 997807 997811 997813
   (6 4 2) has   306 sets:     31 37 41 43 … 997141 997147 997151 997153
```


[User]
The **Sudan function** is a classic example of a recursive function, notable especially because it is not a primitive recursive function. This is also true of the better-known Ackermann function. The Sudan function was the first function having this property to be published.

The Sudan function is usually defined as follows (svg):

F

0
(
x
,
y
)

=
x
+
y

F

n
+
1
(
x
,
0
)

=
x

if
n
≥
0

F

n
+
1
(
x
,
y
+
1
)

=

F

n
(

F

n
+
1
(
x
,
y
)
,

F

n
+
1
(
x
,
y
)
+
y
+
1
)

if
n
≥
0
{\displaystyle {\displaystyle {\begin{array}{lll}F\_{0}(x,y)&=x+y\\F\_{n+1}(x,0)&=x&{\text{if }}n\geq 0\\F\_{n+1}(x,y+1)&=F\_{n}(F\_{n+1}(x,y),F\_{n+1}(x,y)+y+1)&{\text{if }}n\geq 0\\\end{array}}}}

Task

Write a function which returns the value of F(x, y).

[Assistant]
Outputting wiki-tables to more closely emulate the wikipedia examples. Not very efficient but good enough.

```
multi F (0, $x, $y) { $x + $y }
multi F ($n where * > 0, $x, 0) { $x }
multi F ($n, $x, $y) { F($n-1, F($n, $x, $y-1), F($n, $x, $y-1) + $y) }

# Testing
for 0, 6, 1, 15 -> $f, $g {
    my @range = ^$g;
    say "\{|class=\"wikitable\"\n", "|+ F\<sub>$f\</sub> (x,y)\n" ~ '!x\y!!', join '!!', @range;
    -> $r { say "|-\n" ~ '|' ~ join '||', $r, @range.map:{ F($f, $r, $_) } } for @range;
    say( "|}" );
}

```

Output:

F0 (x,y)

| x\y | 0 | 1 | 2 | 3 | 4 | 5 |
| --- | --- | --- | --- | --- | --- | --- |
| 0 | 0 | 1 | 2 | 3 | 4 | 5 |
| 1 | 1 | 2 | 3 | 4 | 5 | 6 |
| 2 | 2 | 3 | 4 | 5 | 6 | 7 |
| 3 | 3 | 4 | 5 | 6 | 7 | 8 |
| 4 | 4 | 5 | 6 | 7 | 8 | 9 |
| 5 | 5 | 6 | 7 | 8 | 9 | 10 |

F1 (x,y)

| x\y | 0 | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 |
| --- | --- | --- | --- | --- | --- | --- | --- | --- | --- | --- | --- | --- | --- | --- | --- |
| 0 | 0 | 1 | 4 | 11 | 26 | 57 | 120 | 247 | 502 | 1013 | 2036 | 4083 | 8178 | 16369 | 32752 |
| 1 | 1 | 3 | 8 | 19 | 42 | 89 | 184 | 375 | 758 | 1525 | 3060 | 6131 | 12274 | 24561 | 49136 |
| 2 | 2 | 5 | 12 | 27 | 58 | 121 | 248 | 503 | 1014 | 2037 | 4084 | 8179 | 16370 | 32753 | 65520 |
| 3 | 3 | 7 | 16 | 35 | 74 | 153 | 312 | 631 | 1270 | 2549 | 5108 | 10227 | 20466 | 40945 | 81904 |
| 4 | 4 | 9 | 20 | 43 | 90 | 185 | 376 | 759 | 1526 | 3061 | 6132 | 12275 | 24562 | 49137 | 98288 |
| 5 | 5 | 11 | 24 | 51 | 106 | 217 | 440 | 887 | 1782 | 3573 | 7156 | 14323 | 28658 | 57329 | 114672 |
| 6 | 6 | 13 | 28 | 59 | 122 | 249 | 504 | 1015 | 2038 | 4085 | 8180 | 16371 | 32754 | 65521 | 131056 |
| 7 | 7 | 15 | 32 | 67 | 138 | 281 | 568 | 1143 | 2294 | 4597 | 9204 | 18419 | 36850 | 73713 | 147440 |
| 8 | 8 | 17 | 36 | 75 | 154 | 313 | 632 | 1271 | 2550 | 5109 | 10228 | 20467 | 40946 | 81905 | 163824 |
| 9 | 9 | 19 | 40 | 83 | 170 | 345 | 696 | 1399 | 2806 | 5621 | 11252 | 22515 | 45042 | 90097 | 180208 |
| 10 | 10 | 21 | 44 | 91 | 186 | 377 | 760 | 1527 | 3062 | 6133 | 12276 | 24563 | 49138 | 98289 | 196592 |
| 11 | 11 | 23 | 48 | 99 | 202 | 409 | 824 | 1655 | 3318 | 6645 | 13300 | 26611 | 53234 | 106481 | 212976 |
| 12 | 12 | 25 | 52 | 107 | 218 | 441 | 888 | 1783 | 3574 | 7157 | 14324 | 28659 | 57330 | 114673 | 229360 |
| 13 | 13 | 27 | 56 | 115 | 234 | 473 | 952 | 1911 | 3830 | 7669 | 15348 | 30707 | 61426 | 122865 | 245744 |
| 14 | 14 | 29 | 60 | 123 | 250 | 505 | 1016 | 2039 | 4086 | 8181 | 16372 | 32755 | 65522 | 131057 | 262128 |


[User]
Task

Solve a partially filled-in normal   9x9   Sudoku grid   and display the result in a human-readable format.

references

* Algorithmics of Sudoku   may help implement this.
* Python Sudoku Solver Computerphile video.

[Assistant]
(formerly Perl 6)

### Brute Force

**Translation of**: Perl

```
my @A = <
    5 3 0  0 2 4  7 0 0
    0 0 2  0 0 0  8 0 0
    1 0 0  7 0 3  9 0 2

    0 0 8  0 7 2  0 4 9
    0 2 0  9 8 0  0 7 0
    7 9 0  0 0 0  0 8 0

    0 0 0  0 3 0  5 0 6
    9 6 0  0 1 0  3 0 0
    0 5 0  6 9 0  0 1 0
>;

my &I = * div 9;  # line number
my &J = * % 9;    # column number
my &K = { ($_ div 27) * 3 + $_ % 9 div 3 }; # bloc number

sub solve {
    for ^@A -> $i {
	next if @A[$i];
	my @taken-values = @A[
	    grep {
		I($_) == I($i) || J($_) == J($i) || K($_) == K($i)
	    }, ^@A
	];
	for grep none(@taken-values), 1..9 {
	    @A[$i] = $_;
	    solve;
	}
	return @A[$i] = 0;
    }
    my $i = 1;
    for ^@A {
	print "@A[$_] ";
	print " "  if $i %% 3;
	print "\n" if $i %% 9;
	print "\n" if $i++ %% 27;
    }
}
solve;

```

Output:

```
5 3 9  8 2 4  7 6 1
6 7 2  1 5 9  8 3 4
1 8 4  7 6 3  9 5 2

3 1 8  5 7 2  6 4 9
4 2 5  9 8 6  1 7 3
7 9 6  3 4 1  2 8 5

8 4 1  2 3 7  5 9 6
9 6 7  4 1 5  3 2 8
2 5 3  6 9 8  4 1 7
```

### Finesse It

This is an alternative solution that uses a more ellaborate set of choices instead of brute-forcing it.

```
#
# In this code, a sudoku puzzle is represented as a two-dimentional
# array. The cells that are not yet solved are represented by yet
# another array of all the possible values.
#
# This implementation is not a simple brute force evaluation of all
# the options, but rather makes four extra attempts to guide the
# solution:
#
#  1) For every change in the grid, usually made by an attempt at a
#     solution, we will reduce the search space of the possible values
#     in all the other cells before going forward.
#
#  2) When a cell that is not yet resolved is the only one that can
#     hold a specific value, resolve it immediately instead of
#     performing the regular search.
#
#  3) Instead of trying from cell 1,1 and moving in sequence, this
#     implementation will start trying on the cell that is the closest
#     to being solved already.
#
#  4) Instead of trying all possible values in sequence, start with
#     the value that is the most unique. I.e.: If the options for this
#     cell are 1,4,6 and 6 is only a candidate for two of the
#     competing cells, we start with that one.
#

# keep a list with all the cells, handy for traversal
my @cells = do for (flat 0..8 X 0..8) -> $x, $y { [ $x, $y ] };

#
# Try to solve this puzzle and return the resolved puzzle if it is at
# all solvable in this configuration.
sub solve($sudoku, Int $level) {
    # cleanup the impossible values first,
    if (cleanup-impossible-values($sudoku, $level)) {
        # try to find implicit answers
        while (find-implicit-answers($sudoku, $level)) {
            # and every time you find some, re-do the cleanup and try again
            cleanup-impossible-values($sudoku, $level);
        }
        # Now let's actually try to solve a new value. But instead of
        # going in sequence, we select the cell that is the closest to
        # being solved already. This will reduce the overall number of
        # guesses.
        for sort { solution-complexity-factor($sudoku, $_[0], $_[1]) },
        grep { $sudoku[$_[0]][$_[1]] ~~ Array },
        @cells -> $cell
        {
            my Int ($x, $y) = @($cell);
            # Now let's try the possible values in the order of
            # uniqueness.
            for sort { matches-in-competing-cells($sudoku, $x, $y, $_) }, @($sudoku[$x][$y]) -> $val {
                trace $level, "Trying $val on "~($x+1)~","~($y+1)~" "~$sudoku[$x][$y].raku;
                my $solution = clone-sudoku($sudoku);
                $solution[$x][$y] = $val;
                my $solved = solve($solution, $level+1);
                if $solved {
                    trace $level, "Solved... ($val on "~($x+1)~","~($y+1)~")";
                    return $solved;
                }
            }
            # if we fell through, it means that we found no valid
            # value for this cell
            trace $level, "Backtrack, path unsolvable... (on "~($x+1)~" "~($y+1)~")";
            return False;
        }
        # all cells are already solved.
        return $sudoku;
    } else {
        # if the cleanup failed, it means this is an invalid grid.
        return False;
    }
}

# This function reduces the search space from values that are already
# assigned to competing cells.
sub cleanup-impossible-values($sudoku, Int $level = 1) {
    my Bool $resolved;
    repeat {
        $resolved = False;
        for grep { $sudoku[$_[0]][$_[1]] ~~ Array },
        @cells -> $cell {
            my Int ($x, $y) = @($cell);
            # which block is this cell in
            my Int $bx = Int($x / 3);
            my Int $by = Int($y / 3);

            # A unfilled cell is not resolved, so it shouldn't match
            my multi match-resolved-cell(Array $other, Int $this) {
                return False;
            }
            my multi match-resolved-cell(Int $other, Int $this) {
                return $other == $this;
            }

            # Reduce the possible values to the ones that are still
            # valid
            my @r =
                grep { !match-resolved-cell($sudoku[any(0..2)+3*$bx][any(0..2)+3*$by], $_) }, # same block
                grep { !match-resolved-cell($sudoku[any(0..8)][$y], $_) }, # same line
                grep { !match-resolved-cell($sudoku[$x][any(0..8)], $_) }, # same column
                @($sudoku[$x][$y]);
            if (@r.elems == 1) {
                # if only one element is left, then make it resolved
                $sudoku[$x][$y] = @r[0];
                $resolved = True;
            } elsif (@r.elems == 0) {
                # This is an invalid grid
                return False;
            } else {
                $sudoku[$x][$y] = @r;
            }
        }
    } while $resolved; # repeat if there was any change
    return True;
}

sub solution-complexity-factor($sudoku, Int $x, Int $y) {
    my Int $bx = Int($x / 3); # this block
    my Int $by = Int($y / 3);
    my multi count-values(Array $val) {
        return $val.elems;
    }
    my multi count-values(Int $val) {
        return 1;
    }
    # the number of possible values should take precedence
    my Int $f = 1000 * count-values($sudoku[$x][$y]);
    for (flat 0..2 X 0..2) -> $lx, $ly {
        $f += count-values($sudoku[$lx+$bx*3][$ly+$by*3])
    }
    for 0..^($by*3), (($by+1)*3)..8 -> $ly {
        $f += count-values($sudoku[$x][$ly])
    }
    for 0..^($bx*3), (($bx+1)*3)..8 -> $lx {
        $f += count-values($sudoku[$lx][$y])
    }
    return $f;
}

sub matches-in-competing-cells($sudoku, Int $x, Int $y, Int $val) {
    my Int $bx = Int($x / 3); # this block
    my Int $by = Int($y / 3);
    # Function to decide which possible value to try first
    my multi cell-matching(Int $cell) {
        return $val == $cell ?? 1 !! 0;
    }
    my multi cell-matching(Array $cell) {
        return $cell.grep({ $val == $_ }) ?? 1 !! 0;
    }
    my Int $c = 0;
    for (flat 0..2 X 0..2) -> $lx, $ly {
        $c += cell-matching($sudoku[$lx+$bx*3][$ly+$by*3])
    }
    for 0..^($by*3), (($by+1)*3)..8 -> $ly {
        $c += cell-matching($sudoku[$x][$ly])
    }
    for 0..^($bx*3), (($bx+1)*3)..8 -> $lx {
        $c += cell-matching($sudoku[$lx][$y])
    }
    return $c;
}

sub find-implicit-answers($sudoku, Int $level) {
    my Bool $resolved = False;
    for grep { $sudoku[$_[0]][$_[1]] ~~ Array },
    @cells -> $cell {
        my Int ($x, $y) = @($cell);
        for @($sudoku[$x][$y]) -> $val {
            # If this is the only cell with this val as a possibility,
            # just make it resolved already
            if (matches-in-competing-cells($sudoku, $x, $y, $val) == 1) {
                $sudoku[$x][$y] = $val;
                $resolved = True;
            }
        }
    }
    return $resolved;
}

my $puzzle =
    map { [ map { $_ == 0 ?? [1..9] !! $_+0  }, @($_) ] },
    [ 0,0,0,0,3,7,6,0,0 ],
    [ 0,0,0,6,0,0,0,9,0 ],
    [ 0,0,8,0,0,0,0,0,4 ],
    [ 0,9,0,0,0,0,0,0,1 ],
    [ 6,0,0,0,0,0,0,0,9 ],
    [ 3,0,0,0,0,0,0,4,0 ],
    [ 7,0,0,0,0,0,8,0,0 ],
    [ 0,1,0,0,0,9,0,0,0 ],
    [ 0,0,2,5,4,0,0,0,0 ];

my $solved = solve($puzzle, 0);
if $solved {
    print-sudoku($solved,0);
} else {
    say "unsolvable.";
}

# Utility functions, not really part of the solution

sub trace(Int $level, Str $message) {
    # say '.' x $level, $message; # un-comment for verbose logging
}

sub clone-sudoku($sudoku) {
    my $clone;
    for (flat 0..8 X 0..8) -> $x, $y {
        $clone[$x][$y] = $sudoku[$x][$y];
    }
    return $clone;
}

sub print-sudoku($sudoku, Int $level = 1) {
    trace $level, '-' x 5*9;
    for @($sudoku) -> $row {
        trace $level, join " ", do for @($row) -> $cell {
            $cell ~~ Array ?? "#{$cell.elems}#" !! " $cell "
        }
    }
}

```

Output:

```
 9   5   4   1   3   7   6   8   2
 2   7   3   6   8   4   1   9   5
 1   6   8   2   9   5   7   3   4
 4   9   5   7   2   8   3   6   1
 6   8   1   4   5   3   2   7   9
 3   2   7   9   6   1   5   4   8
 7   4   9   3   1   2   8   5   6
 5   1   6   8   7   9   4   2   3
 8   3   2   5   4   6   9   1   7

```


[User]
A suffix tree is a data structure commonly used in string algorithms.

Given a string S of length n, its suffix tree is a tree T such that:

* T has exactly n leaves numbered from 1 to n.
* Except for the root, every internal node has at least two children.
* Each edge of T is labelled with a non-empty substring of S.
* No two edges starting out of a node can have string labels beginning with the same character.
* The string obtained by concatenating all the string labels found on the path from the root to leaf i spells out suffix S[i..n], for i from 1 to n.

Such a tree does not exist for all strings. To ensure existence, a character that is not found in S must be appended at its end. The character '$' is traditionally used for this purpose.

For this task, build and display the suffix tree of the string "banana$". Displaying the tree can be done using the code from the visualize a tree task, but any other convenient method is accepted.

There are several ways to implement the tree data structure, for instance how edges should be labelled. Latitude is given in this matter, but notice that a simple way to do it is to label each node with the label of the edge leading to it.

The computation time for an efficient algorithm should be

O
(
n
)
{\displaystyle {\displaystyle O(n)}}
, but such an algorithm might be difficult to implement. An easier,

O
(

n

2
)
{\displaystyle {\displaystyle O(n^{2})}}
 algorithm is accepted.

[Assistant]
(formerly Perl 6)

**Works with**: Rakudo version 2018.04

Here is quite a naive algorithm, probably

O
(

n

2
)
{\displaystyle {\displaystyle O(n^{2})}}
.

The display code is a variant of the visualize a tree task code.

```
multi suffix-tree(Str $str) { suffix-tree flat map &flip, [\~] $str.flip.comb }
multi suffix-tree(@a) {
    hash
    @a == 0 ?? () !!
    @a == 1 ?? ( @a[0] => [] ) !!
    gather for @a.classify(*.substr(0, 1)) {
        my $subtree = suffix-tree(grep *.chars, map *.substr(1), .value[]);
        if $subtree == 1 {
            my $pair = $subtree.pick;
            take .key ~ $pair.key => $pair.value;
        } else {
            take .key => $subtree;
        }
    }
}

my $tree = root => suffix-tree 'banana$';

.say for visualize-tree $tree, *.key, *.value.List;

sub visualize-tree($tree, &label, &children,
                   :$indent = '',
                   :@mid = ('├─', '│ '),
                   :@end = ('└─', '  '),
) {
    sub visit($node, *@pre) {
        gather {
            take @pre[0] ~ $node.&label;
            my @children = sort $node.&children;
            my $end = @children.end;
            for @children.kv -> $_, $child {
                when $end { take visit($child, (@pre[1] X~ @end)) }
                default   { take visit($child, (@pre[1] X~ @mid)) }
            }
        }
    }
    flat visit($tree, $indent xx 2);
}

```

Output:

```
root
├─$
├─a
│ ├─$
│ └─na
│   ├─$
│   └─na$
├─banana$
└─na
  ├─$
  └─na$
```