Find words whose first and last three letters are equal
- Task
Using the dictionary unixdict.txt
find the words whose first and last three letters are equal.
The length of any word shown should have a length > 5.
- Metrics
- 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
11l
L(word) File(‘unixdict.txt’).read().split("\n")
I word.len > 5 & word[0.<3] == word[(len)-3..]
print(word)
- Output:
antiperspirant calendrical einstein hotshot murmur oshkosh tartar testes
Action!
In the following solution the input file unixdict.txt is loaded from H6 drive. Altirra emulator automatically converts CR/LF character from ASCII into 155 character in ATASCII charset used by Atari 8-bit computer when one from H6-H10 hard drive under DOS 2.5 is used.
BYTE FUNC IsValidWord(CHAR ARRAY word)
BYTE len
len=word(0)
IF len<=5 THEN RETURN (0) FI
IF word(1)#word(len-2) THEN RETURN(0) FI
IF word(2)#word(len-1) THEN RETURN(0) FI
IF word(3)#word(len) THEN RETURN(0) FI
RETURN (1)
PROC FindWords(CHAR ARRAY fname)
CHAR ARRAY line(256)
CHAR ARRAY tmp(256)
BYTE dev=[1]
Close(dev)
Open(dev,fname,4)
WHILE Eof(dev)=0
DO
InputSD(dev,line)
IF IsValidWord(line) THEN
PrintE(line)
FI
OD
Close(dev)
RETURN
PROC Main()
CHAR ARRAY fname="H6:UNIXDICT.TXT"
FindWords(fname)
RETURN
- Output:
Screenshot from Atari 8-bit computer
antiperspirant calendrical einstein hotshot murmur oshkosh tartar testes
Ada
with Ada.Text_Io;
with Ada.Strings.Fixed;
procedure Find_Three_Equals is
use Ada.Text_Io;
use Ada.Strings.Fixed;
Filename : constant String := "unixdict.txt";
File : File_Type;
begin
Open (File, In_File, Filename);
while not End_Of_File (File) loop
declare
Word : constant String := Get_Line (File);
First : String renames Head (Word, 3);
Last : String renames Tail (Word, 3);
begin
if First = Last and Word'Length > 5 then
Put_Line (Word);
end if;
end;
end loop;
Close (File);
end Find_Three_Equals;
ALGOL 68
Note, the source of files.incl.a68 is on a separate page on Rosetta Code - see the above link.
BEGIN # find 6 (or more) character words with the same 3 first and last letters
#
PR read "files.incl.a68" PR # include file utilities #
# prints word if it is 6 or more characters long and has the same first #
# and last three characters and returns TRUE if printed, FALSE ptherwise #
# count so far holds the number of matching words detected so far #
PROC show same 3 start and end = ( STRING word, INT count so far )BOOL:
IF INT w len = ( UPB word + 1 ) - LWB word;
w len < 6
THEN FALSE
ELIF word[ 1 : 3 ] /= word[ w len - 2 : ]
THEN FALSE
ELSE print( ( word, " " ) );
IF ( count so far + 1 ) MOD 5 = 0
THEN print( ( newline ) )
ELSE FROM w len + 1 TO 14 DO print( ( " " ) ) OD
FI;
TRUE
FI # show same 3 start and end # ;
IF INT count = "unixdict.txt" EACHLINE show same 3 start and end;
count < 0
THEN
print( ( "Unable to open unixdict.txt", newline ) )
ELSE
print( ( newline, "found ", whole( count, 0 ) ) );
print( ( " words with the same first and last 3 characters" ) );
print( ( newline ) )
FI
END
- Output:
antiperspirant calendrical einstein hotshot murmur oshkosh tartar testes found 8 words with the same first and last 3 characters
AppleScript
on task()
script o
property wrds : words of ¬
(read file ((path to desktop as text) & "www.rosettacode.org:unixdict.txt") as «class utf8»)
property output : {}
end script
repeat with thisWord in o's wrds
if ((thisWord's length > 5) and (thisWord ends with thisWord's text 1 thru 3)) then ¬
set end of o's output to thisWord
end repeat
return o's output's contents
end task
task()
- Output:
{"antiperspirant", "calendrical", "einstein", "hotshot", "murmur", "oshkosh", "tartar", "testes"}
Arturo
words: read.lines relative "unixdict.txt"
equalHeadTail?: function [w][
equal? first.n: 3 w last.n: 3 w
]
loop words 'word [
if 5 < size word [
if equalHeadTail? word ->
print word
]
]
- Output:
antiperspirant calendrical einstein hotshot murmur oshkosh tartar testes
AutoHotkey
FileRead, db, % A_Desktop "\unixdict.txt"
for i, word in StrSplit(db, "`n", "`r")
if StrLen(word) < 6
continue
else if (SubStr(word, 1, 3) = SubStr(word, -2))
result .= word "`n"
MsgBox, 262144, , % result
return
- Output:
antiperspirant calendrical einstein hotshot murmur oshkosh tartar testes
AWK
# syntax: GAWK -f FIND_WORDS_WHICH_FIRST_AND_LAST_THREE_LETTERS_ARE_EQUALS.AWK unixdict.txt
(length($0) >= 6 && substr($0,1,3) == substr($0,length($0)-2,3))
END {
exit(0)
}
- Output:
antiperspirant calendrical einstein hotshot murmur oshkosh tartar testes
C
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
/* "Using the dictionary unixdict.txt" */
#define DICTIONARY_FILE_NAME "unixdict.txt"
/* take into account the first and last 3 letters */
#define CHUNK_LENGTH 3
/* "The length of any word shown should be >5" */
#define MIN_WORD_LENGTH 6
char *create_word_buffer( const char *file_name, size_t *buffer_size );
int wait_for_return( void );
int main() {
size_t buffer_size = 0;
char *buffer = create_word_buffer( DICTIONARY_FILE_NAME, &buffer_size );
if( buffer ) {
FILE *f = fopen( DICTIONARY_FILE_NAME, "r" );
if( f ) {
while( fgets(buffer,buffer_size,f) ) {
size_t l = strlen( buffer );
if( '\n'==buffer[l-1] ) buffer[--l] = '\0';
if( l>=MIN_WORD_LENGTH &&
0==memcmp(buffer,buffer+l-CHUNK_LENGTH,CHUNK_LENGTH) ) {
printf( "%s\n", buffer );
}
}
fclose( f ); f = NULL; /* cleanup */
} else puts( "Couldn't open dictionary file." );
free( buffer ); buffer = NULL; /* cleanup */
} else puts( "Couldn't create word buffer." );
return wait_for_return();
}
/*==============================================================================
No need to verify any parameters in any of the following function - the caller
did his homeworks.
==============================================================================*/
size_t get_line_length( FILE *f ) {
size_t line_length = 0;
int c, ok;
do {
c = fgetc(f);
ok = '\n'!=c&&EOF!=c;
line_length += ok;
} while( ok );
return line_length;
}
size_t find_longest_line_in_file( const char *file_name ) {
size_t max_line_length = ((size_t)-1);
FILE *f = fopen( file_name, "r" );
if( f ) {
max_line_length = 0;
while( !feof(f) ) {
size_t line_length = get_line_length( f );
if( line_length>max_line_length )
max_line_length = line_length;
}
fclose( f ); f = NULL;
}
return max_line_length;
}
char *create_word_buffer( const char *file_name, size_t *buffer_size ) {
char *buffer = NULL;
size_t max_line_length = find_longest_line_in_file( file_name );
if( ((size_t)-1)!=max_line_length ) {
buffer = calloc( max_line_length+2, sizeof(*buffer) );
if( buffer ) *buffer_size = max_line_length+2;
}
return buffer;
}
int wait_for_return( void ) {
puts( "\nPress Return to exit... " );
while( '\n'!=getchar() );
return 0;
}
- Output:
antiperspirant calendrical einstein hotshot murmur oshkosh tartar testes Press Return to exit...
C++
#include <cstdlib>
#include <fstream>
#include <iostream>
int main(int argc, char** argv) {
const char* filename(argc < 2 ? "unixdict.txt" : argv[1]);
std::ifstream in(filename);
if (!in) {
std::cerr << "Cannot open file '" << filename << "'.\n";
return EXIT_FAILURE;
}
std::string word;
int n = 0;
while (getline(in, word)) {
const size_t len = word.size();
if (len > 5 && word.compare(0, 3, word, len - 3) == 0)
std::cout << ++n << ": " << word << '\n';
}
return EXIT_SUCCESS;
}
- Output:
1. antiperspirant 2. calendrical 3. einstein 4. hotshot 5. murmur 6. oshkosh 7. tartar 8. testes
Delphi
Runs in 13 ms.
var Dict: TStringList; {List holds dictionary}
procedure FindFirst3Last3Match(Memo: TMemo);
{Find words where the first and last 3 characters are identical}
var I: integer;
var First3,Last3: string;
begin
for I:=0 to Dict.Count-1 do
if Length(Dict[I])>5 then
begin
First3:=Copy(Dict[I],1,3);
Last3:=Copy(Dict[I],Length(Dict[I])-2,3);
if First3=Last3 then
begin
Memo.Lines.Add(Dict[I]);
end
end;
end;
initialization
{Create/load dictionary}
Dict:=TStringList.Create;
Dict.LoadFromFile('unixdict.txt');
Dict.Sorted:=True;
finalization
Dict.Free;
end.
- Output:
antiperspirant calendrical einstein hotshot murmur oshkosh tartar testes
EasyLang
repeat
s$ = input
until s$ = ""
l = len s$
if l > 5
if substr s$ 1 3 = substr s$ (l - 2) 3
print s$
.
.
.
# the content of unixdict.txt
input_data
10th
.
einstein
.
F#
// First and last three letters are equal. Nigel Galloway: February 18th., 2021
let fN g=if String.length g<6 then false else g.[..2]=g.[g.Length-3..]
seq{use n=System.IO.File.OpenText("unixdict.txt") in while not n.EndOfStream do yield n.ReadLine()}|>Seq.filter fN|>Seq.iter(printfn "%s")
- Output:
antiperspirant calendrical einstein hotshot murmur oshkosh tartar testes
Factor
Read entire file
This version reads the entire dictionary file into memory and filters it. This is the fastest version by far. Factor is optimized for making multiple passes over data; it actually takes longer if we combine the two filters into one, either with short-circuiting or non-short-circuiting and
.
USING: io io.encodings.ascii io.files kernel math sequences ;
"unixdict.txt" ascii file-lines
[ length 5 > ] filter
[ [ 3 head-slice ] [ 3 tail-slice* ] bi = ] filter
[ print ] each
- Output:
antiperspirant calendrical einstein hotshot murmur oshkosh tartar testes
Read file line by line
This version reads the dictionary file line by line and prints out words that fit the criteria. This ends up being a bit more imperative and deeply nested, but unlike the version above, we only load one word at a time, saving quite a bit of memory.
USING: combinators.short-circuit io io.encodings.ascii io.files
kernel math sequences ;
"unixdict.txt" ascii [
[
readln dup
[
dup
{
[ length 5 > ]
[ [ 3 head-slice ] [ 3 tail-slice* ] bi = ]
} 1&&
[ print ] [ drop ] if
] when*
] loop
] with-file-reader
- Output:
As above.
Lazy file I/O
This version lazily reads the input file by treating a stream like a lazy list with the llines
word. This allows us the nice style of the first example with the memory benefits of the second example. Unlike in the first example, combining the filters would buy us some time here, as lazy lists aren't as efficient as sequences.
USING: io io.encodings.ascii io.files kernel lists lists.lazy
math sequences ;
"unixdict.txt" ascii <file-reader> llines
[ length 5 > ] lfilter
[ [ 3 head-slice ] [ 3 tail-slice* ] bi = ] lfilter
[ print ] leach
- Output:
As above.
Forth
: first-last-three-equal { addr len -- ? }
len 5 <= if false exit then
addr 3 addr len 3 - + 3 compare 0= ;
256 constant max-line
: main
0 0 { count fd-in }
s" unixdict.txt" r/o open-file throw to fd-in
begin
here max-line fd-in read-line throw
while
here swap 2dup first-last-three-equal if
count 1+ to count
count 1 .r ." . " type cr
else
2drop
then
repeat
drop
fd-in close-file throw ;
main
bye
- Output:
1. antiperspirant 2. calendrical 3. einstein 4. hotshot 5. murmur 6. oshkosh 7. tartar 8. testes
FreeBASIC
#define NULL 0
type node
word as string*32 'enough space to store any word in the dictionary
nxt as node ptr
end type
function addword( tail as node ptr, word as string ) as node ptr
'allocates memory for a new node, links the previous tail to it,
'and returns the address of the new node
dim as node ptr newnode = allocate(sizeof(node))
tail->nxt = newnode
newnode->nxt = NULL
newnode->word = word
return newnode
end function
function length( word as string ) as uinteger
'necessary replacement for the built-in len function, which in this
'case would always return 32
for i as uinteger = 1 to 32
if asc(mid(word,i,1)) = 0 then return i-1
next i
return 999
end function
dim as string word
dim as node ptr tail = allocate( sizeof(node) )
dim as node ptr head = tail, curr = head, currj
dim as uinteger ln
tail->nxt = NULL
tail->word = "XXXXHEADER"
open "unixdict.txt" for input as #1
while true
line input #1, word
if word = "" then exit while
if length(word)>5 then tail = addword( tail, word )
wend
close #1
while curr->nxt <> NULL
word = curr->word
ln = length(word)
for i as uinteger = 1 to 3
if mid(word,i,1) <> mid(word,ln-3+i,1) then goto nextword
next i
print word
nextword:
curr = curr->nxt
wend
- Output:
antiperspirant calendrical einstein hotshot murmur oshkosh tartar testes
FutureBasic
#plist NSAppTransportSecurity @{NSAllowsArbitraryLoads:YES}
local fn Words as CFArrayRef
CFURLRef url = fn URLWithString( @"http://wiki.puzzlers.org/pub/wordlists/unixdict.txt" )
CFStringRef string = fn StringWithContentsOfURL( url, NSUTF8StringEncoding, NULL )
CFArrayRef array = fn StringComponentsSeparatedByCharactersInSet( string, fn CharacterSetNewlineSet )
PredicateRef predicate = fn PredicateWithFormat( @"self.length > %d", 5 )
end fn = fn ArrayFilteredArrayUsingPredicate( array, predicate )
void local fn DoIt
CFArrayRef words = fn Words
CFStringRef wd
for wd in words
if ( fn StringIsEqual( left(wd,3), right(wd,3) ) )
print wd
end if
next
end fn
fn DoIt
HandleEvents
- Output:
antiperspirant calendrical einstein hotshot murmur oshkosh tartar testes
Go
package main
import (
"bytes"
"fmt"
"io/ioutil"
"log"
"unicode/utf8"
)
func main() {
wordList := "unixdict.txt"
b, err := ioutil.ReadFile(wordList)
if err != nil {
log.Fatal("Error reading file")
}
bwords := bytes.Fields(b)
count := 0
for _, bword := range bwords {
s := string(bword)
if utf8.RuneCountInString(s) > 5 && (s[0:3] == s[len(s)-3:]) {
count++
fmt.Printf("%d: %s\n", count, s)
}
}
}
- Output:
1: antiperspirant 2: calendrical 3: einstein 4: hotshot 5: murmur 6: oshkosh 7: tartar 8: testes
J
>(#~ ((3&{. -: _3&{.)*5<#)@>) cutLF fread 'unixdict.txt'
antiperspirant
calendrical
einstein
hotshot
murmur
oshkosh
tartar
testes
jq
Works with gojq, the Go implementation of jq
select(length > 5 and .[:3] == .[-3:])
- Output:
Invocation example: jq -rRM -f program.jq unixdict.txt
antiperspirant calendrical einstein hotshot murmur oshkosh tartar testes
Julia
See Alternade_words#Julia for the foreachword function.
matchfirstlast3(word, _) = length(word) > 5 && word[1:3] == word[end-2:end] ? word : ""
foreachword("unixdict.txt", matchfirstlast3, numcols=4)
- Output:
Word source: unixdict.txt antiperspirant calendrical einstein hotshot murmur oshkosh tartar testes
Ksh
#!/bin/ksh
# Find list of words (> 5 chars) where 1st 3 and last 3 letters are the same
# # Variables:
#
dict='../unixdict.txt'
integer MIN_LEN=5
integer MATCH_NO=3
######
# main #
######
while read word; do
(( ${#word} <= MIN_LEN )) && continue
first=${word:0:${MATCH_NO}}
last=${word:$((${#word}-MATCH_NO)):${#word}}
[[ ${first} == ${last} ]] && print ${word}
done < ${dict}
- Output:
antiperspirant calendrical einstein hotshot murmur oshkosh tartar testes
Lambdatalk
The unixdict.txt has been loaded from https://web.archive.org and stored in a wiki page, lib_UNIXDICT, from which it can be required on demand in any other one.
{require lib_UNIXDICT}
{def look
{lambda {}
{S.replace \s by {div} in
{S.map {lambda {:w}
{if {and {> {W.length :w} 5}
{W.equal? {W.slice 0 3 :w}
{W.slice -3 {W.length :w} :w} }}
then :w
else}} {S.replace else by el.se in UNIXDICT}} }}}
-> look
{look}
->
antiperspirant
calendrical
einstein
hotshot
murmur
oshkosh
tartar
testes
Note: Due to a "weakness" of the {if then else} special form, where the else separator is not protected, every occurences of the string "else" in the input text must be replaced by some "broken word" before the search, for instance "el.se" and restored after if necessary.
Mathematica /Wolfram Language
dict = Once[Import["https://web.archive.org/web/20180611003215/http://www.puzzlers.org/pub/wordlists/unixdict.txt"]];
dict //= StringSplit[#, "\n"] &;
dict //= Select[StringLength /* GreaterThan[5]];
Select[dict, StringTake[#, 3] === StringTake[#, -3] &]
- Output:
{"antiperspirant", "calendrical", "einstein", "hotshot", "murmur", "oshkosh", "tartar", "testes"}
Nim
for word in "unixdict.txt".lines:
if word.len > 5:
if word[0..2] == word[^3..^1]:
echo word
- Output:
antiperspirant calendrical einstein hotshot murmur oshkosh tartar testes
Nu
open 'unixdict.txt' | split words -l 6 | where $it ends-with ($it | str substring ..2)
- Output:
╭───┬────────────────╮ │ 0 │ antiperspirant │ │ 1 │ calendrical │ │ 2 │ einstein │ │ 3 │ hotshot │ │ 4 │ murmur │ │ 5 │ oshkosh │ │ 6 │ tartar │ │ 7 │ testes │ ╰───┴────────────────╯
Perl
as one-liner ..
// 20210212 Perl programming solution
perl -ne '/(?=^(.{3}).*\1$)^.{6,}$/&&print' unixdict.txt
# minor variation
perl -ne 's/(?=^(.{3}).*\1$)^.{6,}$/print/e' unixdict.txt
Phix
with javascript_semantics function flaste(string word) return length(word)>5 and word[1..3]=word[-3..-1] end function sequence flastes = filter(unix_dict(),flaste) printf(1,"%d words: %s\n",{length(flastes),join(shorten(flastes,"",3))})
- Output:
8 words: antiperspirant calendrical einstein hotshot murmur oshkosh tartar testes
PL/I
firstAndLast3Equal: procedure options(main);
declare dict file;
open file(dict) title('unixdict.txt');
on endfile(dict) stop;
declare word char(32) varying, (first3, last3) char(3);
do while('1'b);
get file(dict) list(word);
first3 = substr(word, 1, 3);
last3 = substr(word, length(word)-2, 3);
if length(word) > 5 & first3 = last3 then
put skip list(word);
end;
end firstAndLast3Equal;
- Output:
antiperspirant calendrical einstein hotshot murmur oshkosh tartar testes
Python
Tested on Python 3+, the file download will work only if the link is still active. It is possible that you may be able to fetch the file in your browser but download via code may still fail. Check whether you are connected to a VPN, it works on open networks
import urllib.request
urllib.request.urlretrieve("http://wiki.puzzlers.org/pub/wordlists/unixdict.txt", "unixdict.txt")
dictionary = open("unixdict.txt","r")
wordList = dictionary.read().split('\n')
dictionary.close()
for word in wordList:
if len(word)>5 and word[:3].lower()==word[-3:].lower():
print(word)
- Output:
antiperspirant calendrical einstein hotshot murmur oshkosh tartar testes
Quackery
[ [] swap ]'[ swap
witheach [
dup nested
unrot over do
iff [ dip join ]
else nip
] drop ] is filter ( [ --> [ )
$ "unixdict.txt" sharefile drop nest$
filter [ size 5 > ]
filter [ 3 split -3 split nip = ]
witheach [ echo$ cr ]
- Output:
antiperspirant calendrical einstein hotshot murmur oshkosh tartar testes
R
dict <- scan("https://web.archive.org/web/20180611003215/http://www.puzzlers.org/pub/wordlists/unixdict.txt", what = character())
dict[nchar(dict) > 5 & substr(dict, 1, 3) == substr(dict, nchar(dict) - 2, nchar(dict))]
Racket
#lang racket
(define ((prefix-and-suffix-match? len) str)
(let ((l (string-length str)))
(and (>= l (* 2 len))
(string=? (substring str 0 len)
(substring str (- l len))))))
(module+ main
(filter (prefix-and-suffix-match? 3) (file->lines "../../data/unixdict.txt")))
- Output:
'("antiperspirant" "calendrical" "einstein" "hotshot" "murmur" "oshkosh" "tartar" "testes")
Raku
# 20210210 Raku programming solution
my ( \L, \N, \IN ) = 5, 3, 'unixdict.txt';
for IN.IO.lines { .say if .chars > L and .substr(0,N) eq .substr(*-N,*) }
- Output:
antiperspirant calendrical einstein hotshot murmur oshkosh tartar testes
Red
Red[]
foreach word read/lines %unixdict.txt [
if all [
greater? length? word 5
equal? take/part copy word 3 take/part/last copy word 3
][
print word
]
]
- Output:
antiperspirant calendrical einstein hotshot murmur oshkosh tartar testes
REXX
This REXX version doesn't care what order the words in the dictionary are in, nor does it care what
case (lower/upper/mixed) the words are in, the search for the words and vowels is caseless.
The program verifies that the first and last three characters are, indeed, letters.
It also allows the length (3) of the first and last number of letters to be specified, and also the minimum length of the
words to be searched on the command line (CL) as well as specifying the dictionary file identifier.
/*REXX pgm finds words in an specified dict. which have the same 1st and last 3 letters.*/
parse arg minL many iFID . /*obtain optional arguments from the CL*/
if minL=='' | minL=="," then minL= 6 /* " " " " " " */
if many=='' | many=="," then many= 3 /* " " " " " " */
if iFID=='' | iFID=="," then iFID='unixdict.txt' /* " " " " " " */
do #=1 while lines(iFID)\==0 /*read each word in the file (word=X).*/
x= strip( linein( iFID) ) /*pick off a word from the input line. */
@.#= x /*save: the original case of the word.*/
end /*#*/
#= # - 1 /*adjust word count because of DO loop.*/
say copies('─', 30) # "words in the dictionary file: " iFID
finds= 0 /*word count which have matching end. */
/*process all the words that were found*/
do j=1 for #; $= @.j; upper $ /*obtain dictionary word; uppercase it.*/
if length($)<minL then iterate /*Word not long enough? Then skip it.*/
lhs= left($, many); rhs= right($, many) /*obtain the left & right side of word.*/
if \datatype(lhs || rhs, 'U') then iterate /*are the left and right side letters? */
if lhs \== rhs then iterate /*Left side match right side? No, skip*/
finds= finds + 1 /*bump count of only "e" vowels found. */
say right( left(@.j, 30), 40) /*indent original word for readability.*/
end /*j*/
/*stick a fork in it, we're all done. */
say copies('─', 30) finds " words found that the left " many ' letters match the' ,
"right letters which a word has a minimal length of " minL
- output when using the default inputs:
────────────────────────────── 25104 words in the dictionary file: unixdict.txt antiperspirant calendrical einstein hotshot murmur oshkosh tartar testes ────────────────────────────── 8 words found that the left 3 letters match the right letters which a word has a minimal length of 6
Ring
load "stdlib.ring"
cStr = read("unixdict.txt")
wordList = str2list(cStr)
num = 0
see "working..." + nl
see "Words are:" + nl
ln = len(wordList)
for n = ln to 1 step -1
if len(wordList[n]) < 6
del(wordList,n)
ok
next
for n = 1 to len(wordList)
if left(wordList[n],3) = right(wordList[n],3)
num = num + 1
see "" + num + ". " + wordList[n] + nl
ok
next
see "done..." + nl
Output:
working... Words are: 1. antiperspirant 2. calendrical 3. einstein 4. hotshot 5. murmur 6. oshkosh 7. tartar 8. testes done...
RPL
The only way to use unixdict.txt as input is to convert it into a list of 25104 strings. Luckily, emulators can handle such a big data structure in RAM.
≪ { }
1 UnixDict SIZE FOR j ‘UnixDict’ j GET IF DUP SIZE 5 ≤ THEN DROP ELSE DUP 1 3 SUB OVER DUP SIZE DUP 2 - SWAP SUB IF == THEN + ELSE DROP END END NEXT ≫ ≫ ‘SAME3’ STO
- Output:
1: { "antiperspirant" "calendrical" "einstein" "hotshot" "murmur" "oshkosh" "tartar" "testes" }
Ruby
puts File.readlines("unixdict.txt", chomp: true).select{|w| w.end_with?(w[0,3]) && w.size > 5}
- Output:
antiperspirant calendrical einstein hotshot murmur oshkosh tartar testes
Rust
use std::fs;
fn firstsamelast(word: &&str, min_same: usize) -> bool {
let n = word.len();
return n >= 2 * min_same && word[..min_same] == word[n - min_same..];
}
fn main() {
let wordsfile = fs::read_to_string("unixdict.txt").unwrap().to_lowercase();
let words = wordsfile.split_whitespace().filter(|w| firstsamelast(w, 3));
for (i, w) in words.enumerate() {
print!("{:<16}{}", w, if (i + 1) % 4 == 0 { "\n" } else { "" });
}
return ();
}
- Output:
antiperspirant calendrical einstein hotshot murmur oshkosh tartar testes
sed
/^\(...\).*\1$/!d
- Output:
$ sed -f ends3eq.sed unixdict.txt antiperspirant calendrical einstein hotshot murmur oshkosh tartar testes
Sidef
File("unixdict.txt").open_r.each {|word|
word.len > 5 || next
if (word.ends_with(word.first(3))) {
say word
}
}
- Output:
antiperspirant calendrical einstein hotshot murmur oshkosh tartar testes
Swift
import Foundation
do {
try String(contentsOfFile: "unixdict.txt", encoding: String.Encoding.ascii)
.components(separatedBy: "\n")
.filter{$0.count > 5 && $0.prefix(3) == $0.suffix(3)}
.enumerated()
.forEach{print("\($0.0 + 1). \($0.1)")}
} catch {
print(error.localizedDescription)
}
- Output:
1. antiperspirant 2. calendrical 3. einstein 4. hotshot 5. murmur 6. oshkosh 7. tartar 8. testes
VBScript
After building a program checking for the 3 letters in any order, I found people just checked the same trigraph at start and end. I modified my program so it puts an asterisk after the words in the "standard" answer. Run the ssript with CScript.
with createobject("ADODB.Stream")
.charset ="UTF-8"
.open
.loadfromfile("unixdict.txt")
s=.readtext
end with
a=split (s,vblf)
set d= createobject("Scripting.Dictionary")
for each aa in a
x=trim(aa)
l=len(x)
if l>5 then
d.removeall
for i=1 to 3
m=mid(x,i,1)
if not d.exists(m) then d.add m,null
next
res=true
for i=l-2 to l
m=mid(x,i,1)
if not d.exists(m) then
res=false:exit for
else
d.remove(m)
end if
next
if res then
wscript.stdout.write left(x & space(15),15)
if left(x,3)=right(x,3) then wscript.stdout.write "*"
wscript.stdout.writeline
end if
end if
next
- Output:
alfalfa antiperspirant * calendrical * cataract deadhead earthenware einstein * encumbrance greenberg hannah hotshot * marjoram murmur * oshkosh * tartar * teammate tenement testes *
V (Vlang)
import os
fn main() {
mut result :=''
unixdict := os.read_file('./unixdict.txt') or {println('Error: file not found') exit(1)}
for word in unixdict.split_into_lines() {
if word.len > 5 {
if word.substr(0, 3) == word.substr(word.len - 3, word.len) {
result += word + '\n'
}
}
}
println(result)
}
- Output:
antiperspirant calendrical einstein hotshot murmur oshkosh tartar testes
Wren
import "io" for File
import "./fmt" for Fmt
var wordList = "unixdict.txt" // local copy
var count = 0
File.read(wordList).trimEnd().split("\n").
where { |w|
return w.count > 5 && (w[0..2] == w[-3..-1])
}.
each { |w|
count = count + 1
Fmt.print("$d: $s", count, w)
}
- Output:
1: antiperspirant 2: calendrical 3: einstein 4: hotshot 5: murmur 6: oshkosh 7: tartar 8: testes
XPL0
string 0; \Use zero-terminated strings
int I, Ch, Len;
char Word(100); \(longest word in unixdict.txt is 22 chars)
def LF=$0A, CR=$0D, EOF=$1A;
[FSet(FOpen("unixdict.txt", 0), ^I); \open dictionary and set it to device 3
OpenI(3);
repeat I:= 0;
loop [repeat Ch:= ChIn(3) until Ch # CR; \remove possible CR
if Ch=LF or Ch=EOF then quit;
Word(I):= Ch;
I:= I+1;
];
Word(I):= 0; \terminate string
Len:= I;
if Len >= 6 then
if Word(0) = Word(Len-3) &
Word(1) = Word(Len-2) &
Word(2) = Word(Len-1) then
[Text(0, Word); CrLf(0)];
until Ch = EOF;
]
- Output:
antiperspirant calendrical einstein hotshot murmur oshkosh tartar testes
- Draft Programming Tasks
- 11l
- Action!
- Ada
- ALGOL 68
- ALGOL 68-files
- AppleScript
- Arturo
- AutoHotkey
- AWK
- C
- C++
- Delphi
- SysUtils,StdCtrls
- EasyLang
- F Sharp
- Factor
- Forth
- FreeBASIC
- FutureBasic
- Go
- J
- Jq
- Julia
- Ksh
- Lambdatalk
- Mathematica
- Wolfram Language
- Nim
- Nu
- Perl
- Phix
- PL/I
- Python
- Quackery
- R
- Racket
- Raku
- Red
- REXX
- Ring
- RPL
- Ruby
- Rust
- Sed
- Sidef
- Swift
- VBScript
- V (Vlang)
- Wren
- Wren-fmt
- XPL0