-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathbashflashcards.sh
executable file
·151 lines (131 loc) · 4.79 KB
/
bashflashcards.sh
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
#!/bin/bash
##### USER SETTINGS #####
MAXTYPOS=1
SEP="[:space:];," # grep word/meaning separator
#########################
# measures difference between two words for typo checking
function levenshtein {
if [ "$#" -ne "2" ]; then
echo "Usage: $0 word1 word2" >&2
elif [ "${#1}" -lt "${#2}" ]; then
levenshtein "$2" "$1"
else
local str1len=$((${#1}))
local str2len=$((${#2}))
local d i j
for i in $(seq 0 $(((str1len+1)*(str2len+1)))); do
d[i]=0
done
for i in $(seq 0 $((str1len))); do
d[$((i+0*str1len))]=$i
done
for j in $(seq 0 $((str2len))); do
d[$((0+j*(str1len+1)))]=$j
done
for j in $(seq 1 $((str2len))); do
for i in $(seq 1 $((str1len))); do
[ "${1:i-1:1}" = "${2:j-1:1}" ] && local cost=0 || local cost=1
local del=$((d[(i-1)+str1len*j]+1))
local ins=$((d[i+str1len*(j-1)]+1))
local alt=$((d[(i-1)+str1len*(j-1)]+cost))
d[i+str1len*j]=$(echo -e "$del\n$ins\n$alt" | sort -n | head -1)
done
done
echo ${d[str1len+str1len*(str2len)]}
fi
}
REVERSE="false"
FILES="$@"
if [[ " --reverse -r " =~ " $1 " ]]; then
REVERSE="true"
FILES="$(echo "$@" | sed "s/^[^ ]* //g")"
fi
if [ -p /dev/stdin ]; then
MYINPUT="$(</dev/stdin)"
elif [[ " --help -help -h " =~ " $1 " || "$1" == "" ]]; then
echo "$0 [OPTION] file1.txt [file2.txt] .. [fileN.txt]"
echo "OPTION: -r -reverse Switches between asking for the vocabulary word or the meaning of it."
exit -1
else
for file in $FILES; do
if ! file $file | grep -q "text"; then
echo "$file doesn't appear to be a text file! Exiting.."
exit 1
fi
done
MYINPUT="$(IFS=' ' cat $FILES)"
fi
LINESLEFT="$(echo "$MYINPUT" | shuf)"
# stats
WRONGCTR="0"
WRONGARR=()
while [[ "$LINESLEFT" != "" ]]; do
NEWLINES=""
while read -u 66 line; do
if [[ "$line" =~ ^"#" ]]; then continue
elif echo "$line" | grep -q "^[^${SEP}]\+[${SEP}]\+[^${SEP}]\+.*$"; then
WORD=("$(echo "$line" | grep -osa "^[^${SEP}]*")")
WORDS=("$WORD")
NOMEANING=(); IFS=',' read -r -a NOMEANING <<< "$(echo "$line" | sed "s/^[^${SEP}]*[${SEP}]\+//g" | sed "s/, /,/g")"
MEANINGS=(); for i in "${NOMEANING[@]}"; do if [[ "$(echo "$i" | sed "s/[[:space:]\"]*//g")" != "" ]]; then MEANINGS+=("$i"); fi; done
if [[ "$REVERSE" == "true" ]]; then
TEMPVAR=("${WORDS[@]}")
WORDS=("${MEANINGS[@]}")
MEANINGS=("${TEMPVAR[@]}")
askwords="$(echo ${WORDS[@]} | sed 's/ /, /g')"
else
askwords="${WORDS[0]}"
fi
MEANINGSPRINT="$(IFS=','; printf '%s\n' "${MEANINGS[*]}" | sed "s/,/, /g")"
# this adds alternative spellings to the list of correct solutions, in form of: (i)kala(gb) -> kala, ikalagb, kalagb, ikala
# can only handle up to two parenthesis correctly and will sort of ignore the ones in the middle
for i in "${MEANINGS[@]}"; do
if echo "$i" | grep -osaq "(.\+)"; then
for j in `echo "$(echo "$i" | sed "s/\(.*\)([^\(\)]\+)/\1/") \
$(echo "$i" | sed "s/([^\(\)]\+)//") \
$(echo "$i" | sed "s/([^\(\)]\+)//g") \
$(echo "$i")" | sed "s/[\(\)]*//g" | xargs -n1 | sort -u | xargs`; do
MEANINGS+=("$j")
done
fi
done
TEMPVAR="$( echo " $askwords " | sed -e :a -e 's/^.\{1,41\}$/=&=/;ta' )"
while [ ${#TEMPVAR} -lt 43 ]; do TEMPVAR="=$TEMPVAR"; done
echo "$TEMPVAR"
read -p "ANSWER: " answer </dev/tty
echo "$MEANINGSPRINT"
WRONG="true"
for meaning in "${MEANINGS[@]}"; do
meaning="$(echo "$meaning" | sed "s/[[:space:]\"]*//g")"
answer="$(echo "$answer" | sed "s/[[:space:]\"]*//g")"
# iconv transcribes characters to the next best ASCII thing, used for checking if the answer is sort of correct
simpmeaning="$(echo "$meaning" | iconv -f utf-8 -t ascii//TRANSLIT | sed "s/[^A-z0-9\-\_]//g")"
simpanswer="$(echo "$answer" | iconv -f utf-8 -t ascii//TRANSLIT | sed "s/[^A-z0-9\-\_]//g")"
if [ "$(levenshtein "$simpmeaning" "$simpanswer")" -lt "$(($MAXTYPOS+1))" ] || [[ "$meaning" == "$answer" ]]; then
WRONG="false"
echo " :)++RIGHT++(:"
break
fi
done
if [[ "$WRONG" == "true" ]]; then
WRONGCTR="$(($WRONGCTR + 1))"
WRONGARR+=("$WORD")
echo " --:(WRONG):--"
NEWLINES="$(echo -e "$line\n$NEWLINES")"
fi
fi
done 66< <(echo "$LINESLEFT" | shuf)
LINESLEFT="$NEWLINES"
if [[ "$LINESLEFT" != "" ]]; then
echo "--->Still $(echo "$LINESLEFT" | wc -l ) to go!"
fi
done
if [[ "$LINESLEFT" == "" ]]; then
echo "ALL DONE! AWESOME!"
if [ "$WRONGCTR" -gt "0" ]; then
echo "STATS: $WRONGCTR wrong answers."
echo "STATS: Wrong words: $(echo "${WRONGARR[*]}" | tr ' ' '\n' | sort -u | tr '\n' ' ')"
else
echo "YOU MADE ZERO MISTAKES!"
fi
fi