tasks a-s
This commit is contained in:
parent
47bf37c096
commit
b83f433714
12433 changed files with 156208 additions and 123 deletions
8
Task/Semordnilap/0DESCRIPTION
Normal file
8
Task/Semordnilap/0DESCRIPTION
Normal file
|
|
@ -0,0 +1,8 @@
|
|||
A [http://en.wikipedia.org/wiki/Semordnilap#Semordnilaps semordnilap], is a word (or phrase) that spells a different word (or phrase) backward. "Semordnilap" is a word that itself is a semordnilap.
|
||||
|
||||
Example: <code>''lager'' and ''regal''</code>
|
||||
|
||||
Using only words from the [http://www.puzzlers.org/pub/wordlists/unixdict.txt unixdict], report the total number of unique semordnilap pairs, and print 5 examples. (Note that lager/regal and regal/lager should be counted as one unique pair.)
|
||||
|
||||
;Cf.
|
||||
* [[Palindrome_detection|Palindrome detection]]
|
||||
2
Task/Semordnilap/1META.yaml
Normal file
2
Task/Semordnilap/1META.yaml
Normal file
|
|
@ -0,0 +1,2 @@
|
|||
---
|
||||
note: Semordnilap
|
||||
20
Task/Semordnilap/AWK/semordnilap.awk
Normal file
20
Task/Semordnilap/AWK/semordnilap.awk
Normal file
|
|
@ -0,0 +1,20 @@
|
|||
# syntax: GAWK -f SEMORDNILAP.AWK unixdict.txt
|
||||
{ arr[$0]++ }
|
||||
END {
|
||||
PROCINFO["sorted_in"] = "@ind_str_asc"
|
||||
for (word in arr) {
|
||||
rword = ""
|
||||
for (j=length(word); j>0; j--) {
|
||||
rword = rword substr(word,j,1)
|
||||
}
|
||||
if (word == rword) { continue } # palindrome
|
||||
if (rword in arr) {
|
||||
if (word in shown || rword in shown) { continue }
|
||||
shown[word]++
|
||||
shown[rword]++
|
||||
if (n++ < 5) { printf("%s %s\n",word,rword) }
|
||||
}
|
||||
}
|
||||
printf("%d words\n",n)
|
||||
exit(0)
|
||||
}
|
||||
19
Task/Semordnilap/Ada/semordnilap-1.ada
Normal file
19
Task/Semordnilap/Ada/semordnilap-1.ada
Normal file
|
|
@ -0,0 +1,19 @@
|
|||
with Ada.Containers.Indefinite_Vectors, Ada.Text_IO;
|
||||
|
||||
package String_Vectors is
|
||||
|
||||
package String_Vec is new Ada.Containers.Indefinite_Vectors
|
||||
(Index_Type => Positive, Element_Type => String);
|
||||
|
||||
type Vec is new String_Vec.Vector with null record;
|
||||
|
||||
function Read(Filename: String) return Vec;
|
||||
-- uses Ada.Text_IO to read words from the given file into a Vec
|
||||
-- requirement: each word is written in a single line
|
||||
|
||||
function Is_In(List: Vec;
|
||||
Word: String;
|
||||
Start: Positive; Stop: Natural) return Boolean;
|
||||
-- checks if Word is in List(Start .. Stop);
|
||||
-- requirement: the words in List are sorted alphabetically
|
||||
end String_Vectors;
|
||||
35
Task/Semordnilap/Ada/semordnilap-2.ada
Normal file
35
Task/Semordnilap/Ada/semordnilap-2.ada
Normal file
|
|
@ -0,0 +1,35 @@
|
|||
package body String_Vectors is
|
||||
|
||||
function Is_In(List: Vec;
|
||||
Word: String;
|
||||
Start: Positive; Stop: Natural) return Boolean is
|
||||
Middle: Positive;
|
||||
begin
|
||||
if Start > Stop then
|
||||
return False;
|
||||
else
|
||||
Middle := (Start+Stop) / 2;
|
||||
if List.Element(Middle) = Word then
|
||||
return True;
|
||||
elsif List.Element(Middle) < Word then
|
||||
return List.Is_In(Word, Middle+1, Stop);
|
||||
else
|
||||
return List.Is_In(Word, Start, Middle-1);
|
||||
end if;
|
||||
end if;
|
||||
end Is_In;
|
||||
|
||||
function Read(Filename: String) return Vec is
|
||||
package IO renames Ada.Text_IO;
|
||||
Persistent_List: IO.File_Type;
|
||||
List: Vec;
|
||||
begin
|
||||
IO.Open(File => Persistent_List, Name => Filename, Mode => IO.In_File);
|
||||
while not IO.End_Of_File(Persistent_List) loop
|
||||
List.Append(New_Item => IO.Get_Line(Persistent_List));
|
||||
end loop;
|
||||
IO.Close(Persistent_List);
|
||||
return List;
|
||||
end Read;
|
||||
|
||||
end String_Vectors;
|
||||
30
Task/Semordnilap/Ada/semordnilap-3.ada
Normal file
30
Task/Semordnilap/Ada/semordnilap-3.ada
Normal file
|
|
@ -0,0 +1,30 @@
|
|||
with String_Vectors, Ada.Text_IO, Ada.Command_Line;
|
||||
|
||||
procedure Semordnilap is
|
||||
|
||||
function Backward(S: String) return String is
|
||||
begin
|
||||
if S'Length < 2 then
|
||||
return S;
|
||||
else
|
||||
return (S(S'Last) & Backward(S(S'First+1 .. S'Last-1)) & S(S'First));
|
||||
end if;
|
||||
end Backward;
|
||||
|
||||
W: String_Vectors.Vec := String_Vectors.Read(Ada.Command_Line.Argument(1));
|
||||
|
||||
Semi_Counter: Natural := 0;
|
||||
|
||||
begin
|
||||
for I in W.First_Index .. W.Last_Index loop
|
||||
if W.Element(I) /= Backward(W.Element(I)) and then
|
||||
W.Is_In(Backward(W.Element(I)), W.First_Index, I) then
|
||||
Semi_Counter := Semi_Counter + 1;
|
||||
if Semi_Counter <= 5 then
|
||||
Ada.Text_IO.Put_Line(W.Element(I) & " - " & Backward(W.Element(I)));
|
||||
end if;
|
||||
end if;
|
||||
end loop;
|
||||
Ada.Text_IO.New_Line;
|
||||
Ada.Text_IO.Put("pairs found:" & Integer'Image(Semi_Counter));
|
||||
end Semordnilap;
|
||||
50
Task/Semordnilap/BBC-BASIC/semordnilap.bbc
Normal file
50
Task/Semordnilap/BBC-BASIC/semordnilap.bbc
Normal file
|
|
@ -0,0 +1,50 @@
|
|||
INSTALL @lib$+"SORTLIB"
|
||||
Sort% = FN_sortinit(0,0)
|
||||
|
||||
DIM dict$(26000*2)
|
||||
|
||||
REM Load the dictionary, eliminating palindromes:
|
||||
dict% = OPENIN("C:\unixdict.txt")
|
||||
IF dict%=0 ERROR 100, "No dictionary file"
|
||||
index% = 0
|
||||
REPEAT
|
||||
A$ = GET$#dict%
|
||||
B$ = FNreverse(A$)
|
||||
IF A$<>B$ THEN
|
||||
dict$(index%) = A$
|
||||
dict$(index%+1) = B$
|
||||
index% += 2
|
||||
ENDIF
|
||||
UNTIL EOF#dict%
|
||||
CLOSE #dict%
|
||||
Total% = index%
|
||||
|
||||
REM Sort the dictionary:
|
||||
C% = Total%
|
||||
CALL Sort%, dict$(0)
|
||||
|
||||
REM Find semordnilaps:
|
||||
pairs% = 0
|
||||
examples% = 0
|
||||
FOR index% = 0 TO Total%-2
|
||||
IF dict$(index%)=dict$(index%+1) THEN
|
||||
IF examples%<5 IF LEN(dict$(index%))>4 THEN
|
||||
PRINT dict$(index%) " " FNreverse(dict$(index%))
|
||||
examples% += 1
|
||||
ENDIF
|
||||
pairs% += 1
|
||||
ENDIF
|
||||
NEXT
|
||||
|
||||
PRINT "Total number of unique pairs = "; pairs%/2
|
||||
END
|
||||
|
||||
DEF FNreverse(A$)
|
||||
LOCAL I%, L%, P%
|
||||
IF A$="" THEN =""
|
||||
L% = LENA$ - 1
|
||||
P% = !^A$
|
||||
FOR I% = 0 TO L% DIV 2
|
||||
SWAP P%?I%, L%?(P%-I%)
|
||||
NEXT
|
||||
= A$
|
||||
29
Task/Semordnilap/C++/semordnilap.cpp
Normal file
29
Task/Semordnilap/C++/semordnilap.cpp
Normal file
|
|
@ -0,0 +1,29 @@
|
|||
#include <fstream>
|
||||
#include <iostream>
|
||||
#include <set>
|
||||
#include <string>
|
||||
|
||||
int main()
|
||||
{
|
||||
std::ifstream input("unixdict.txt");
|
||||
if (!input) {
|
||||
return 1; // couldn't open input file
|
||||
}
|
||||
|
||||
std::set<std::string> words; // previous words
|
||||
std::string word; // current word
|
||||
size_t count = 0; // pair count
|
||||
|
||||
while (input >> word) {
|
||||
std::string drow(word.rbegin(), word.rend()); // reverse
|
||||
if (words.find(drow) == words.end()) { // pair not found
|
||||
words.insert(word);
|
||||
} else { // pair found
|
||||
if (count < 5) {
|
||||
std::cout << word << ' ' << drow << '\n';
|
||||
}
|
||||
++count;
|
||||
}
|
||||
}
|
||||
std::cout << "\nSemordnilap pairs: " << count << '\n';
|
||||
}
|
||||
66
Task/Semordnilap/C/semordnilap.c
Normal file
66
Task/Semordnilap/C/semordnilap.c
Normal file
|
|
@ -0,0 +1,66 @@
|
|||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <alloca.h> /* stdlib.h might not have obliged. */
|
||||
#include <string.h>
|
||||
|
||||
static void reverse(char *s, int len)
|
||||
{
|
||||
int i, j;
|
||||
char tmp;
|
||||
|
||||
for (i = 0, j = len - 1; i < len / 2; ++i, --j)
|
||||
tmp = s[i], s[i] = s[j], s[j] = tmp;
|
||||
}
|
||||
|
||||
/* Wrap strcmp() for qsort(). */
|
||||
static int strsort(const void *s1, const void *s2)
|
||||
{
|
||||
return strcmp(*(char **) s1, *(char **) s2);
|
||||
}
|
||||
|
||||
int main(void)
|
||||
{
|
||||
int i, c, ct = 0, len, sem = 0;
|
||||
char **words, **drows, tmp[24];
|
||||
FILE *dict = fopen("unixdict.txt", "r");
|
||||
|
||||
/* Determine word count. */
|
||||
while ((c = fgetc(dict)) != EOF)
|
||||
ct += c == '\n';
|
||||
rewind(dict);
|
||||
|
||||
/* Using alloca() is generally discouraged, but we're not doing
|
||||
* anything too fancy and the memory gains are significant. */
|
||||
words = alloca(ct * sizeof words);
|
||||
drows = alloca(ct * sizeof drows);
|
||||
|
||||
for (i = 0; fscanf(dict, "%s%n", tmp, &len) != EOF; ++i) {
|
||||
/* Use just enough memory to store the next word. */
|
||||
strcpy(words[i] = alloca(len), tmp);
|
||||
|
||||
/* Store it again, then reverse it. */
|
||||
strcpy(drows[i] = alloca(len), tmp);
|
||||
reverse(drows[i], len - 1);
|
||||
}
|
||||
|
||||
fclose(dict);
|
||||
qsort(drows, ct, sizeof drows, strsort);
|
||||
|
||||
/* Walk both sorted lists, checking only the words which could
|
||||
* possibly be a semordnilap pair for the current reversed word. */
|
||||
for (c = i = 0; i < ct; ++i) {
|
||||
while (strcmp(drows[i], words[c]) > 0 && c < ct - 1)
|
||||
c++;
|
||||
/* We found a semordnilap. */
|
||||
if (!strcmp(drows[i], words[c])) {
|
||||
strcpy(tmp, drows[i]);
|
||||
reverse(tmp, strlen(tmp));
|
||||
/* Unless it was a palindrome. */
|
||||
if (strcmp(drows[i], tmp) > 0 && sem++ < 5)
|
||||
printf("%s\t%s\n", drows[i], tmp);
|
||||
}
|
||||
}
|
||||
|
||||
printf("Semordnilap pairs: %d\n", sem);
|
||||
return 0;
|
||||
}
|
||||
17
Task/Semordnilap/D/semordnilap.d
Normal file
17
Task/Semordnilap/D/semordnilap.d
Normal file
|
|
@ -0,0 +1,17 @@
|
|||
import std.stdio, std.file, std.string, std.algorithm;
|
||||
|
||||
void main() {
|
||||
bool[string] seenWords;
|
||||
size_t pairCount = 0;
|
||||
|
||||
foreach (word; readText("unixdict.txt").toLower().splitter()) {
|
||||
auto drow = word.dup.reverse;
|
||||
if (drow in seenWords) {
|
||||
if (pairCount++ < 5)
|
||||
writeln(word, " ", drow);
|
||||
} else
|
||||
seenWords[word] = true;
|
||||
}
|
||||
|
||||
writeln("\nSemordnilap pairs: ", pairCount);
|
||||
}
|
||||
58
Task/Semordnilap/Go/semordnilap.go
Normal file
58
Task/Semordnilap/Go/semordnilap.go
Normal file
|
|
@ -0,0 +1,58 @@
|
|||
package main
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"io/ioutil"
|
||||
"log"
|
||||
"strings"
|
||||
)
|
||||
|
||||
func main() {
|
||||
// read file into memory as one big block
|
||||
data, err := ioutil.ReadFile("unixdict.txt")
|
||||
if err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
// copy the block, split it up into words
|
||||
words := strings.Split(string(data), "\n")
|
||||
// optional, free the first block for garbage collection
|
||||
data = nil
|
||||
// put words in a map, also determine length of longest word
|
||||
m := make(map[string]bool)
|
||||
longest := 0
|
||||
for _, w := range words {
|
||||
m[string(w)] = true
|
||||
if len(w) > longest {
|
||||
longest = len(w)
|
||||
}
|
||||
}
|
||||
// allocate a buffer for reversing words
|
||||
r := make([]byte, longest)
|
||||
// iterate over word list
|
||||
sem := 0
|
||||
var five []string
|
||||
for _, w := range words {
|
||||
// first, delete from map. this prevents a palindrome from matching
|
||||
// itself, and also prevents it's reversal from matching later.
|
||||
delete(m, w)
|
||||
// use buffer to reverse word
|
||||
last := len(w) - 1
|
||||
for i := 0; i < len(w); i++ {
|
||||
r[i] = w[last-i]
|
||||
}
|
||||
rs := string(r[:len(w)])
|
||||
// see if reversed word is in map, accumulate results
|
||||
if m[rs] {
|
||||
sem++
|
||||
if len(five) < 5 {
|
||||
five = append(five, w+"/"+rs)
|
||||
}
|
||||
}
|
||||
}
|
||||
// print results
|
||||
fmt.Println(sem, "pairs")
|
||||
fmt.Println("examples:")
|
||||
for _, e := range five {
|
||||
fmt.Println(" ", e)
|
||||
}
|
||||
}
|
||||
9
Task/Semordnilap/Groovy/semordnilap-1.groovy
Normal file
9
Task/Semordnilap/Groovy/semordnilap-1.groovy
Normal file
|
|
@ -0,0 +1,9 @@
|
|||
def semordnilapWords(source) {
|
||||
def words = [] as Set
|
||||
def semordnilaps = []
|
||||
source.eachLine { word ->
|
||||
if (words.contains(word.reverse())) semordnilaps << word
|
||||
words << word
|
||||
}
|
||||
semordnilaps
|
||||
}
|
||||
3
Task/Semordnilap/Groovy/semordnilap-2.groovy
Normal file
3
Task/Semordnilap/Groovy/semordnilap-2.groovy
Normal file
|
|
@ -0,0 +1,3 @@
|
|||
def semordnilaps = semordnilapWords(new URL('http://www.puzzlers.org/pub/wordlists/unixdict.txt'))
|
||||
println "Found ${semordnilaps.size()} semordnilap words"
|
||||
semordnilaps[0..<5].each { println "$it -> ${it.reverse()}" }
|
||||
10
Task/Semordnilap/Haskell/semordnilap.hs
Normal file
10
Task/Semordnilap/Haskell/semordnilap.hs
Normal file
|
|
@ -0,0 +1,10 @@
|
|||
import qualified Data.Set as S
|
||||
|
||||
semordnilaps = snd . foldl f (S.empty,[]) where
|
||||
f (s,w) x | S.member (reverse x) s = (s, x:w)
|
||||
| otherwise = (S.insert x s, w)
|
||||
|
||||
main=do s <- readFile "unixdict.txt"
|
||||
let l = semordnilaps (lines s)
|
||||
print $ length l
|
||||
mapM_ print $ map (\x->(x, reverse x)) $ take 5 l
|
||||
4
Task/Semordnilap/J/semordnilap-1.j
Normal file
4
Task/Semordnilap/J/semordnilap-1.j
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
isSemordnilap=: |.&.> (~: *. e.) ]
|
||||
unixdict=: <;._2 freads 'unixdict.txt'
|
||||
#semordnilaps=: ~. /:~"1 (,. |.&.>) (#~ isSemordnilap) unixdict
|
||||
158
|
||||
12
Task/Semordnilap/J/semordnilap-2.j
Normal file
12
Task/Semordnilap/J/semordnilap-2.j
Normal file
|
|
@ -0,0 +1,12 @@
|
|||
(5?.158) { semordnilaps
|
||||
┌────┬────┐
|
||||
│kay │yak │
|
||||
├────┼────┤
|
||||
│nat │tan │
|
||||
├────┼────┤
|
||||
│avis│siva│
|
||||
├────┼────┤
|
||||
│flow│wolf│
|
||||
├────┼────┤
|
||||
│caw │wac │
|
||||
└────┴────┘
|
||||
30
Task/Semordnilap/Java/semordnilap.java
Normal file
30
Task/Semordnilap/Java/semordnilap.java
Normal file
|
|
@ -0,0 +1,30 @@
|
|||
import java.io.*;
|
||||
import java.util.*;
|
||||
|
||||
public class Semordnilaps {
|
||||
|
||||
public static void main(String[] args) throws IOException {
|
||||
List<String> lst = readLines("unixdict.txt");
|
||||
Set<String> seen = new HashSet<>();
|
||||
int count = 0;
|
||||
for (String w : lst) {
|
||||
String r = new StringBuilder(w).reverse().toString();
|
||||
if (seen.contains(r)) {
|
||||
if (count++ < 5)
|
||||
System.out.printf("%-10s %-10s\n", w, r);
|
||||
} else seen.add(w);
|
||||
}
|
||||
System.out.println("\nSemordnilap pairs found: " + count);
|
||||
}
|
||||
|
||||
private static List<String> readLines(String fn) throws IOException {
|
||||
List<String> lines;
|
||||
try (BufferedReader br = new BufferedReader(new FileReader(fn))) {
|
||||
lines = new ArrayList<>();
|
||||
String line;
|
||||
while ((line = br.readLine()) != null)
|
||||
lines.add(line.trim().toLowerCase());
|
||||
}
|
||||
return lines;
|
||||
}
|
||||
}
|
||||
4
Task/Semordnilap/Julia/semordnilap.julia
Normal file
4
Task/Semordnilap/Julia/semordnilap.julia
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
raw = readdlm("unixdict.txt",String)[:]
|
||||
inter = intersect(raw,map(reverse,raw)) #find the matching strings/revstrings
|
||||
res = String[b == 1 && a != reverse(a) && a < reverse(a) ? a : reverse(a) for a in inter, b in 1:2] #create pairs
|
||||
res = res[res[:,1] .!= res[:,2],:] #get rid of duplicates, palindromes
|
||||
44
Task/Semordnilap/Liberty-BASIC/semordnilap.liberty
Normal file
44
Task/Semordnilap/Liberty-BASIC/semordnilap.liberty
Normal file
|
|
@ -0,0 +1,44 @@
|
|||
print "Loading dictionary."
|
||||
open "unixdict.txt" for input as #1
|
||||
while not(eof(#1))
|
||||
line input #1, a$
|
||||
dict$=dict$+" "+a$
|
||||
wend
|
||||
close #1
|
||||
|
||||
print "Dictionary loaded."
|
||||
print "Seaching for semordnilaps."
|
||||
|
||||
semo$=" " 'string to hold words with semordnilaps
|
||||
|
||||
do
|
||||
i=i+1
|
||||
w$=word$(dict$,i)
|
||||
p$=reverseString$(w$)
|
||||
if w$<>p$ then
|
||||
p$=" "+p$+" "
|
||||
if instr(semo$,p$) = 0 then
|
||||
if instr(dict$,p$) then
|
||||
pairs=pairs+1
|
||||
print w$+" /"+p$
|
||||
semo$=semo$+w$+p$
|
||||
end if
|
||||
end if
|
||||
end if
|
||||
scan
|
||||
loop until w$=""
|
||||
|
||||
print "Total number of unique semordnilap pairs is ";pairs
|
||||
wait
|
||||
|
||||
Function isPalindrome(string$)
|
||||
string$ = Lower$(string$)
|
||||
reverseString$ = reverseString$(string$)
|
||||
If string$ = reverseString$ Then isPalindrome = 1
|
||||
End Function
|
||||
|
||||
Function reverseString$(string$)
|
||||
For i = Len(string$) To 1 Step -1
|
||||
reverseString$ = reverseString$ + Mid$(string$, i, 1)
|
||||
Next i
|
||||
End Function
|
||||
3
Task/Semordnilap/Mathematica/semordnilap.math
Normal file
3
Task/Semordnilap/Mathematica/semordnilap.math
Normal file
|
|
@ -0,0 +1,3 @@
|
|||
data = Import["http://www.puzzlers.org/pub/wordlists/unixdict.txt", "List"];
|
||||
result = DeleteDuplicates[ Select[data, MemberQ[data, StringReverse[#]] && # =!= StringReverse[#] &], (# ===StringReverse[#2]) &];
|
||||
Print[Length[result], Take[result, 5]]
|
||||
29
Task/Semordnilap/NetRexx/semordnilap.netrexx
Normal file
29
Task/Semordnilap/NetRexx/semordnilap.netrexx
Normal file
|
|
@ -0,0 +1,29 @@
|
|||
/* NetRexx */
|
||||
options replace format comments java crossref symbols nobinary
|
||||
|
||||
/* REXX ***************************************************************
|
||||
* 07.09.2012 Walter Pachl
|
||||
**********************************************************************/
|
||||
fid = 'unixdict.txt' /* the test dictionary */
|
||||
ifi = File(fid)
|
||||
ifr = BufferedReader(FileReader(ifi))
|
||||
have = '' /* words encountered */
|
||||
pi = 0 /* number of palindromes */
|
||||
loop label j_ forever /* as long there is input */
|
||||
line = ifr.readLine /* read a line (String) */
|
||||
if line = null then leave j_ /* NULL indicates EOF */
|
||||
w = Rexx(line) /* each line contains 1 word */
|
||||
If w > '' Then Do /* not a blank line */
|
||||
r = w.reverse /* reverse it */
|
||||
If have[r] > '' Then Do /* was already encountered */
|
||||
pi = pi + 1 /* increment number of pal's */
|
||||
If pi <= 5 Then /* the first 5 are listed */
|
||||
Say have[r] w
|
||||
End
|
||||
have[w] = w /* remember the word */
|
||||
End
|
||||
end j_
|
||||
ifr.close
|
||||
|
||||
Say pi 'words in' fid 'have a palindrome' /* total number found */
|
||||
return
|
||||
34
Task/Semordnilap/OCaml/semordnilap.ocaml
Normal file
34
Task/Semordnilap/OCaml/semordnilap.ocaml
Normal file
|
|
@ -0,0 +1,34 @@
|
|||
module StrSet = Set.Make(String)
|
||||
|
||||
let str_rev s =
|
||||
let len = String.length s in
|
||||
let r = String.create len in
|
||||
for i = 0 to len - 1 do
|
||||
r.[i] <- s.[len - 1 - i]
|
||||
done;
|
||||
(r)
|
||||
|
||||
let input_line_opt ic =
|
||||
try Some (input_line ic)
|
||||
with End_of_file -> close_in ic; None
|
||||
|
||||
let () =
|
||||
let ic = open_in "unixdict.txt" in
|
||||
let rec aux set acc =
|
||||
match input_line_opt ic with
|
||||
| Some word ->
|
||||
let rev = str_rev word in
|
||||
if StrSet.mem rev set
|
||||
then aux set ((word, rev) :: acc)
|
||||
else aux (StrSet.add word set) acc
|
||||
| None ->
|
||||
(acc)
|
||||
in
|
||||
let pairs = aux StrSet.empty [] in
|
||||
let len = List.length pairs in
|
||||
Printf.printf "Semordnilap pairs: %d\n" len;
|
||||
Random.self_init ();
|
||||
for i = 1 to 5 do
|
||||
let (word, rev) = List.nth pairs (Random.int len) in
|
||||
Printf.printf " %s %s\n" word rev
|
||||
done
|
||||
15
Task/Semordnilap/PHP/semordnilap.php
Normal file
15
Task/Semordnilap/PHP/semordnilap.php
Normal file
|
|
@ -0,0 +1,15 @@
|
|||
<?php
|
||||
// Read dictionary into array
|
||||
$dictionary = array_fill_keys(file(
|
||||
'http://www.puzzlers.org/pub/wordlists/unixdict.txt',
|
||||
FILE_IGNORE_NEW_LINES | FILE_SKIP_EMPTY_LINES
|
||||
), true);
|
||||
foreach (array_keys($dictionary) as $word) {
|
||||
$reversed_word = strrev($word);
|
||||
if (isset($dictionary[$reversed_word]) && $word > $reversed_word)
|
||||
$words[$word] = $reversed_word;
|
||||
}
|
||||
echo count($words), "\n";
|
||||
// array_rand() returns keys, not values
|
||||
foreach (array_rand($words, 5) as $word)
|
||||
echo "$word $words[$word]\n";
|
||||
41
Task/Semordnilap/PL-I/semordnilap.pli
Normal file
41
Task/Semordnilap/PL-I/semordnilap.pli
Normal file
|
|
@ -0,0 +1,41 @@
|
|||
find: procedure options (main); /* 20/1/2013 */
|
||||
declare word character (20) varying controlled;
|
||||
declare dict(*) character (20) varying controlled;
|
||||
declare 1 pair controlled,
|
||||
2 a character (20) varying, 2 b character (20) varying;
|
||||
declare (i, j) fixed binary;
|
||||
declare in file;
|
||||
|
||||
open file(in) title ('/UNIXDICT.TXT,type(LF),recsize(100)');
|
||||
on endfile (in) go to completed_read;
|
||||
do forever;
|
||||
allocate word;
|
||||
get file (in) edit (word) (L);
|
||||
end;
|
||||
|
||||
completed_read:
|
||||
free word; /* because at the final allocation, no word was stored. */
|
||||
allocate dict(allocation(word));
|
||||
do i = 1 to hbound(dict,1);
|
||||
dict(i) = word; free word;
|
||||
end;
|
||||
|
||||
/* Search dictionary for pairs: */
|
||||
do i = 1 to hbound(dict,1)-1;
|
||||
do j = i+1 to hbound(dict,1);
|
||||
if length(dict(i)) = length(dict(j)) then
|
||||
do;
|
||||
if dict(i) = reverse(dict(j)) then
|
||||
do;
|
||||
allocate pair; pair.a = dict(i); pair.b = dict(j);
|
||||
end;
|
||||
end;
|
||||
end;
|
||||
end;
|
||||
|
||||
put skip list ('There are ' || trim(allocation(pair)) || ' pairs.');
|
||||
|
||||
do while (allocation(pair) > 0);
|
||||
put skip edit (pair) (a, col(20), a); free pair;
|
||||
end;
|
||||
end find;
|
||||
8
Task/Semordnilap/Perl-6/semordnilap.pl6
Normal file
8
Task/Semordnilap/Perl-6/semordnilap.pl6
Normal file
|
|
@ -0,0 +1,8 @@
|
|||
my \words = set slurp("unixdict.txt").lines;
|
||||
|
||||
my \sems = gather for words.list -> \word {
|
||||
my \drow = word.flip;
|
||||
take [word,drow] if drow ∈ words and drow lt word;
|
||||
}
|
||||
|
||||
.say for +sems, sems.pick(5);
|
||||
7
Task/Semordnilap/Perl/semordnilap.pl
Normal file
7
Task/Semordnilap/Perl/semordnilap.pl
Normal file
|
|
@ -0,0 +1,7 @@
|
|||
while (<>) {
|
||||
chomp;
|
||||
my $r = reverse;
|
||||
$seen{$r}++ and $c++ < 5 and print "$_ $r\n" or $seen{$_}++;
|
||||
}
|
||||
|
||||
print "$c\n"
|
||||
11
Task/Semordnilap/Python/semordnilap-1.py
Normal file
11
Task/Semordnilap/Python/semordnilap-1.py
Normal file
|
|
@ -0,0 +1,11 @@
|
|||
>>> with open('unixdict.txt') as f:
|
||||
wordset = set(f.read().strip().split())
|
||||
|
||||
>>> revlist = (''.join(word[::-1]) for word in wordset)
|
||||
>>> pairs = set((wrd, rev) for wrd, rev in zip(wordset, revlist)
|
||||
if wrd < rev and rev in wordset)
|
||||
>>> len(pairs)
|
||||
158
|
||||
>>> sorted(pairs, key=lambda p: (len(p[0]), p))[-5:]
|
||||
[('damon', 'nomad'), ('lager', 'regal'), ('leper', 'repel'), ('lever', 'revel'), ('kramer', 'remark')]
|
||||
>>>
|
||||
16
Task/Semordnilap/Python/semordnilap-2.py
Normal file
16
Task/Semordnilap/Python/semordnilap-2.py
Normal file
|
|
@ -0,0 +1,16 @@
|
|||
import os
|
||||
import random
|
||||
# Load file and put it to dictionary as set
|
||||
dictionary = {word.rstrip(os.linesep) for word in open('unixdict.txt')}
|
||||
|
||||
# List of results
|
||||
results = []
|
||||
for word in dictionary:
|
||||
# [::-1] reverses string
|
||||
reversed_word = word[::-1]
|
||||
if reversed_word in dictionary and word > reversed_word:
|
||||
results.append((word, reversed_word))
|
||||
|
||||
print(len(results))
|
||||
for words in random.sample(results, 5):
|
||||
print(' '.join(words))
|
||||
19
Task/Semordnilap/REXX/semordnilap-1.rexx
Normal file
19
Task/Semordnilap/REXX/semordnilap-1.rexx
Normal file
|
|
@ -0,0 +1,19 @@
|
|||
/* REXX ***************************************************************
|
||||
* 07.09.2012 Walter Pachl
|
||||
**********************************************************************/
|
||||
fid='unixdict.txt' /* the test dictionary */
|
||||
have.='' /* words encountered */
|
||||
pi=0 /* number of palindromes */
|
||||
Do li=1 By 1 While lines(fid)>0 /* as long there is input */
|
||||
w=linein(fid) /* read a word */
|
||||
If w>'' Then Do /* not a blank line */
|
||||
r=reverse(w) /* reverse it */
|
||||
If have.r>'' Then Do /* was already encountered */
|
||||
pi=pi+1 /* increment number of pal's */
|
||||
If pi<=5 Then /* the first 5 ale listed */
|
||||
Say have.r w
|
||||
End
|
||||
have.w=w /* remember the word */
|
||||
End
|
||||
End
|
||||
Say pi 'words in' fid 'have a palindrome' /* total number found */
|
||||
15
Task/Semordnilap/REXX/semordnilap-2.rexx
Normal file
15
Task/Semordnilap/REXX/semordnilap-2.rexx
Normal file
|
|
@ -0,0 +1,15 @@
|
|||
/*REXX program finds palindrome pairs using a dictionary (UNIXDICT.TXT)*/
|
||||
#=0 /*number of palindromes (so far).*/
|
||||
parse arg iFID .; if iFID=='' then iFID='UNIXDICT.TXT' /*use default?*/
|
||||
@.= /*caseless non-duplicated words. */
|
||||
do while lines(ifid)\==0; _=linein(iFID); u=translate(space(_,0))
|
||||
if length(u)<2 | @.u\=='' then iterate /*can't be a unique pal.*/
|
||||
r=reverse(u)
|
||||
if @.r\=='' then do; #=#+1 /*found palindrome pair.*/
|
||||
if #<6 then say @.r',' _ /*only list first 5 pals*/
|
||||
end
|
||||
@.u=_
|
||||
end /*while*/
|
||||
say /*a unique palindrome pair = a semordnilap*/
|
||||
say "There're" # 'unique palindrome pairs in the dictionary file:' iFID
|
||||
/*stick a fork in it, we're done.*/
|
||||
9
Task/Semordnilap/Ruby/semordnilap.rb
Normal file
9
Task/Semordnilap/Ruby/semordnilap.rb
Normal file
|
|
@ -0,0 +1,9 @@
|
|||
DICT=File.readlines("unixdict.txt").collect{|line| line.tr("\n", "")}
|
||||
res=[]
|
||||
i = 0
|
||||
DICT.collect {|z| z.reverse}.sort.each {|z|
|
||||
i+=1 while z > DICT[i] and i < DICT.length-1
|
||||
res.push z if z.eql?(DICT[i]) and z < z.reverse
|
||||
}
|
||||
puts "There are #{res.length} semordnilaps, of which the following are 5:"
|
||||
res.sample(5).each {|z| puts "#{z} #{z.reverse}"}
|
||||
23
Task/Semordnilap/TUSCRIPT/semordnilap.tuscript
Normal file
23
Task/Semordnilap/TUSCRIPT/semordnilap.tuscript
Normal file
|
|
@ -0,0 +1,23 @@
|
|||
$$ MODE TUSCRIPT,{}
|
||||
requestdata = REQUEST ("http://www.puzzlers.org/pub/wordlists/unixdict.txt")
|
||||
DICT semordnilap CREATE 99999
|
||||
COMPILE
|
||||
LOOP r=requestdata
|
||||
rstrings=STRINGS(r," ? ")
|
||||
rreverse=REVERSE(rstrings)
|
||||
revstring=EXCHANGE (rreverse,":'':':'::")
|
||||
group=APPEND (r,revstring)
|
||||
sort=ALPHA_SORT (group)
|
||||
DICT semordnilap APPEND/QUIET/COUNT sort,num,cnt,"",""
|
||||
ENDLOOP
|
||||
DICT semordnilap UNLOAD wordgroups,num,howmany
|
||||
get_palins=FILTER_INDEX (howmany,-," 1 ")
|
||||
size=SIZE(get_palins)
|
||||
PRINT "unixdict.txt contains ", size, " palindromes"
|
||||
PRINT " "
|
||||
palindromes=SELECT (wordgroups,#get_palins)
|
||||
LOOP n=1,5
|
||||
take5=SELECT (palindromes,#n)
|
||||
PRINT n,". ",take5
|
||||
ENDLOOP
|
||||
ENDCOMPILE
|
||||
30
Task/Semordnilap/Tcl/semordnilap.tcl
Normal file
30
Task/Semordnilap/Tcl/semordnilap.tcl
Normal file
|
|
@ -0,0 +1,30 @@
|
|||
package require Tcl 8.5
|
||||
package require http
|
||||
|
||||
# Fetch the words
|
||||
set t [http::geturl http://www.puzzlers.org/pub/wordlists/unixdict.txt]
|
||||
set wordlist [split [http::data $t] \n]
|
||||
http::cleanup $t
|
||||
|
||||
# Build hash table for speed
|
||||
foreach word $wordlist {
|
||||
set reversed([string reverse $word]) "dummy"
|
||||
}
|
||||
|
||||
# Find where a reversal exists
|
||||
foreach word $wordlist {
|
||||
if {[info exists reversed($word)] && $word ne [string reverse $word]} {
|
||||
# Remove to prevent pairs from being printed twice
|
||||
unset reversed([string reverse $word])
|
||||
# Add to collection of pairs
|
||||
set pairs($word/[string reverse $word]) "dummy"
|
||||
}
|
||||
}
|
||||
set pairlist [array names pairs] ;# NB: pairs are in *arbitrary* order
|
||||
|
||||
# Report what we've found
|
||||
puts "Found [llength $pairlist] reversed pairs"
|
||||
foreach pair $pairlist {
|
||||
puts "Example: $pair"
|
||||
if {[incr i]>=5} break
|
||||
}
|
||||
60
Task/Semordnilap/XPL0/semordnilap.xpl0
Normal file
60
Task/Semordnilap/XPL0/semordnilap.xpl0
Normal file
|
|
@ -0,0 +1,60 @@
|
|||
include c:\cxpl\codes; \intrinsic 'code' declarations
|
||||
string 0; \use zero-terminated strings
|
||||
def LF=$0A, CR=$0D, EOF=$1A;
|
||||
|
||||
proc RevStr(S); \Reverse order of characters in a string
|
||||
char S;
|
||||
int I, J, T;
|
||||
[J:= 0;
|
||||
while S(J) do J:= J+1;
|
||||
J:= J-1;
|
||||
I:= 0;
|
||||
while I<J do
|
||||
[T:= S(I); S(I):= S(J); S(J):= T; \swap
|
||||
I:= I+1; J:= J-1;
|
||||
];
|
||||
];
|
||||
|
||||
func StrEqual(S1, S2); \Compare strings, return 'true' if equal
|
||||
char S1, S2;
|
||||
int I;
|
||||
[for I:= 0 to 80-1 do
|
||||
[if S1(I) # S2(I) then return false;
|
||||
if S1(I) = 0 then return true;
|
||||
];
|
||||
];
|
||||
|
||||
int C, I, J, SJ, Count;
|
||||
char Dict, Word(80);
|
||||
[\Read file on command line redirected as input, i.e: <unixdict.txt
|
||||
Dict:= GetHp; \starting address of block of local "heap" memory
|
||||
I:= 0; \ [GetHp does exact same thing as Reserve(0)]
|
||||
repeat repeat C:= ChIn(1) until C#LF; \get chars sans line feeds
|
||||
if C = CR then C:= 0; \replace carriage return with terminator
|
||||
Dict(I):= C; I:= I+1;
|
||||
until C = EOF;
|
||||
SetHp(Dict+I); \set heap pointer beyond Dict
|
||||
I:= 0; Count:= 0;
|
||||
loop [J:= 0; \get word at I
|
||||
repeat C:= Dict(I+J); Word(J):= C; J:= J+1;
|
||||
until C=0;
|
||||
RevStr(Word);
|
||||
J:= J+I; \set J to following word in Dict
|
||||
if Dict(J) = EOF then quit;
|
||||
SJ:= J; \save index to following word
|
||||
loop [if StrEqual(Word, Dict+J) then
|
||||
[Count:= Count+1;
|
||||
if Count <= 5 then
|
||||
[RevStr(Word); \show some examples
|
||||
Text(0, Word); ChOut(0, ^ ); Text(0, Dict+J); CrLf(0);
|
||||
];
|
||||
quit;
|
||||
];
|
||||
repeat J:= J+1 until Dict(J) = 0;
|
||||
J:= J+1;
|
||||
if Dict(J) = EOF then quit;
|
||||
];
|
||||
I:= SJ; \next word
|
||||
];
|
||||
IntOut(0, Count); CrLf(0);
|
||||
]
|
||||
Loading…
Add table
Add a link
Reference in a new issue