Code Golf: Code 39 Code Bar
-
25-09-2019 - |
Question
Le défi
Le code le plus court par nombre de caractères pour dessiner une représentation ASCII d'un code 39 code à barres.
article Wikipedia Code 39: http://en.wikipedia.org/wiki/Code_39
Entrée
L'entrée sera une chaîne de caractères juridiques pour le code 39 codes à barres. Cela signifie 43 caractères sont valides: 0
-9
A
-Z
(espace) et
-.$/+%
. Le caractère *
ne sera pas apparaître dans l'entrée car il est utilisé comme démarrage et d'arrêt des caractères.
Sortie
Chaque caractère codé dans le code 39 codes à barres ont neuf éléments, cinq barres et quatre espaces. Bars seront représentés avec des caractères #
et espaces seront représentés par le caractère espace. Trois des neuf éléments seront grandes. Les éléments étroits seront un caractère large et les éléments larges seront trois caractères larges. Un espace entre les caractères d'un seul espace doit être ajouté entre chaque configuration de caractère. Le motif doit être répété de sorte que la hauteur du code à barres est de huit caractères élevé.
serait représentée comme le démarrage / arrêt caractère *
(bWbwBwBwb) ceci:
# # ### ### #
# # ### ### #
# # ### ### #
# # ### ### #
# # ### ### #
# # ### ### #
# # ### ### #
# # ### ### #
^ ^ ^^ ^ ^ ^ ^^^
| | || | | | |||
narrow bar -+ | || | | | |||
wide space ---+ || | | | |||
narrow bar -----+| | | | |||
narrow space ------+ | | | |||
wide bar --------+ | | |||
narrow space ----------+ | |||
wide bar ------------+ |||
narrow space --------------+||
narrow bar ---------------+|
inter-character space ----------------+
- Le début et caractère
*
devront être émis au début et à la fin du code à barres. - Pas d'espace calme devra être inclus avant ou après le code à barres.
- Aucun chiffre de contrôle devra être calculé.
- encodage Code39 ASCII complet n'est pas nécessaire, à seulement 43 caractères standard.
- Aucun texte doit être imprimé en dessous de la représentation de code à barres ASCII pour identifier le contenu de sortie.
- Le
#
de caractère peut être remplacé par un autre caractère de densité plus élevée si on le souhaite. En utilisant le caractère de bloc complet U + 2588, permettrait le code à barres pour scanner réellement lors de l'impression.
Les cas de test
Input:
ABC
Output:
# # ### ### # ### # # # ### # ### # # ### ### ### # # # # # ### ### #
# # ### ### # ### # # # ### # ### # # ### ### ### # # # # # ### ### #
# # ### ### # ### # # # ### # ### # # ### ### ### # # # # # ### ### #
# # ### ### # ### # # # ### # ### # # ### ### ### # # # # # ### ### #
# # ### ### # ### # # # ### # ### # # ### ### ### # # # # # ### ### #
# # ### ### # ### # # # ### # ### # # ### ### ### # # # # # ### ### #
# # ### ### # ### # # # ### # ### # # ### ### ### # # # # # ### ### #
# # ### ### # ### # # # ### # ### # # ### ### ### # # # # # ### ### #
Input:
1/3
Output:
# # ### ### # ### # # # ### # # # # # ### ### # # # # # ### ### #
# # ### ### # ### # # # ### # # # # # ### ### # # # # # ### ### #
# # ### ### # ### # # # ### # # # # # ### ### # # # # # ### ### #
# # ### ### # ### # # # ### # # # # # ### ### # # # # # ### ### #
# # ### ### # ### # # # ### # # # # # ### ### # # # # # ### ### #
# # ### ### # ### # # # ### # # # # # ### ### # # # # # ### ### #
# # ### ### # ### # # # ### # # # # # ### ### # # # # # ### ### #
# # ### ### # ### # # # ### # # # # # ### ### # # # # # ### ### #
Input:
- $ (minus space dollar)
Output:
# # ### ### # # # # ### ### # ### # ### # # # # # # # # ### ### #
# # ### ### # # # # ### ### # ### # ### # # # # # # # # ### ### #
# # ### ### # # # # ### ### # ### # ### # # # # # # # # ### ### #
# # ### ### # # # # ### ### # ### # ### # # # # # # # # ### ### #
# # ### ### # # # # ### ### # ### # ### # # # # # # # # ### ### #
# # ### ### # # # # ### ### # ### # ### # # # # # # # # ### ### #
# # ### ### # # # # ### ### # ### # ### # # # # # # # # ### ### #
# # ### ### # # # # ### ### # ### # ### # # # # # # # # ### ### #
nombre de code comprend entrée / sortie (programme complet).
La solution
J, 102 caractères
8#,:' #'{~,0,.~#:(3 u:'䝝啕啕啕䑅儑啕啕啕啕䗝䔑啕䕷煝䑑凝瑗屗眕凗瑵屵具瑝屝啕啕啕啕啕啕啕甗崗睅圗病巅呷甝崝圝畇嵇睑均痑巑嗇畱嵱坱煗䝗燕䗗煵䝵'){~32-~a.i.'*'(,,[)
Explication. Lire à partir du haut en bas:.
8#,: NB. Copy 8 times
' #'{~ NB. Turn binary 0 and 1 into space and #
, NB. Link the array into a list
0,.~ NB. Append a 0 to the end of each row of the array.
#: NB. Turn the list of numbers into a binary array where each row is the base-2 representation of the corresponding number
(3 u:'䝝啕啕啕䑅儑啕啕啕啕䗝䔑啕䕷煝䑑凝瑗屗眕凗瑵屵具瑝屝啕啕啕啕啕啕啕甗崗睅圗病巅呷甝崝圝畇嵇睑均痑巑嗇畱嵱坱煗䝗燕䗗煵䝵') NB. Turn this wchar string into a list of ints in range 0-65535.
{~ NB. Select numbers from the string-list whose indices are...
32-~ NB. ... 32 less than ...
a.i. NB. ... the ascii values of ...
'*'(,,[) NB. ... the input string with a '*' on either side!
Autres conseils
Ruby (1,9) - 121 132 141 166 170 289 < s> 295
BONNETS-off à David
puts"*#{$_}*
".tr(" --9*$+%A-Z","䝝䕷煝䑑凝瑗屗眕凗瑵屵具瑝屝䗝䑅䔑儑甗崗睅圗病巅呷甝崝圝畇嵇睑均痑巑嗇畱嵱坱煗䝗燕䗗煵䝵").gsub(/./){|c|c.ord.to_s(2).tr"01"," #"}*8
echo "ABC" | ruby -ne 'puts"*#{$_}*
".tr(" --9*$+%A-Z","䝝䕷煝䑑凝瑗屗眕凗瑵屵具瑝屝䗝䑅䔑儑甗崗睅圗病巅呷甝崝圝畇嵇睑均痑巑嗇畱嵱坱煗䝗燕䗗煵䝵").gsub(/./){|c|c.ord.to_s(2).tr"01"," #"}*8'
stocke Seuls les 44 caractères requis et utilise la fonction de translittération de Ruby à la carte ces
<space>
<-> to <9>
<*>
<$>
<+>
<%>
<A> to <Z>
pour les valeurs codées.
Python, 304 caractères
Pas de fantaisie compression Unicode. Seule astuce consiste à réorganiser les caractères de maximiser le chevauchement. Mon premier programme Python.
b="BWbwbwBwbWBwbwbwBWbwBwbwbWBwbwBwbWbwBwbwBWbwbwBWBwbwbwbWBwBwbwbWbwBwBwbWbwbwBwBWbwbwbwBWBwbWbWbWbwbWbWbWb"
s=t=""
for x in"*"+raw_input()+"*":
i=".NI5VRD9YLH4 OB8XSE2?J6WKG0ZMA7*PC1-TF3UQ????$/+%".find(x)*2
s+=b[i:i+9]+"w"
for x in s:t+=["#"," ","###"," "]["bwBW".find(x)]
for k in b[-8:]:print(t)
Assembleur
monte à 220 octets.
mov di,ds
mov al,42
call a3
mov dh,[80h]
mov si,82h
a1:lodsb
call a3
dec dh
jnz a1
mov al,42
call a3
mov ax,2573
stosw
mov al,36
stosb
mov cl,8
a2:mov dx,ds
mov ah,9
int 21h
loop a2
a3:sub al,97
cmp al,26
ja a4
sub al,32
a4:mov bx,a6-3
a8:add bx,3
cmp bx,a7
jae ret
cmp al,[bx]
jne a8
mov bp,[bx+1]
a5:rcr bp,1
mov al,36
sbb al,0
and al,35
stosb
or bp,bp
jnz a5
mov al,32
stosb
ret
a6:dd 0D05DC5CFh,01DD17517h,05477D275h,0D475C5D3h,01DD55717h,07745D657h,0D85D17D7h,057E05D1Dh
dd 0745DE174h,0E35177E2h,0D7E47475h,051DDE551h,0E77715E6h,05DE85C57h,05C75E95Ch,0EB7157EAh
dd 077EC715Dh,07175ED45h,0EF45D7EEh,0D5F045DDh,04757F171h,0F3475DF2h,047F44775h,07571F575h
dd 0F755C7F6h,047F875D1h,05771F957h,0CD7751CCh,071BF5D47h,05111C35Dh,0CA4511CEh,045C44451h
dd 05DD1C944h
a7:
Pas beaucoup à faire pour faire des tours intelligents ici.
Python 3.1, sans Unicode (213 215 223 240 248 249 caractères)
o=""
for c in"%r"%input():
u="W3YZ56C$EF. 89'0HIJM/OP+%RSTUV12X4ABD-7GKLNQ".find(c);n=sum(b"))&&&,(*&2&&&)),&/8(*&1)<&/V&&&)),&/5);D&/S"[u:])-930+35*u
while n:o+="###"[n%2*2:]+" "[n&2:];n>>=2
print((o+"\n")*8)
Explication:
Le code 39 séquence est codée dans un nombre en base 4 (gauche plupart = le moins significatif) avec:
-
bw
→ 3 -
Bw
→ 2 -
bW
→ 1 -
BW
→ 0
La séquence est ensuite triée, par exemple.
20333 Q
21233 N
21323 L
...
La différence des entrées adjacentes sont prises, ce qui donne une liste comme [48, 12, 3, …]
. Ensuite 35
est ajouté à cette liste pour assurer que les chiffres se situent dans la plage ASCII. Cela donne à la chaîne de "))&&&,…"
.
Ce code a également pris avantagées du *
ne figurera pas dans l'entrée, afin que nous puissions le remplacer par un caractère non valide, y compris '
. Dans CPython repr("ABC") == "'ABC'"
, afin que nous puissions nous débarrasser de 2 caractères.
Python 3.1, avec Unicode (154 158 CHARS)
Basé sur la solution J , en profitant de la « le #
de caractères peut être remplacé par un autre caractère de densité plus élevée si on le souhaite » règle, en définissant la densité comme zone de parties sombres divisé par le rectangle englobant le plus petit du glyphe . :)
print((''.join(" #"[int(c)]for d in"%r"%input()for c in bin(2*ord("䝝啕啕啕䑅儑啕䗝啕啕啕䔑啕䕷煝䑑凝瑗屗眕凗瑵屵具瑝屝啕啕啕啕啕啕啕甗崗睅圗病巅呷甝崝圝畇嵇睑均痑巑嗇畱嵱坱煗䝗燕䗗煵䝵"[ord(d)-32]))[2:])+"\n")*8)
Python (2.6) - 430 312 302 caractères
Troisième aller au problème, encore une place pour l'amélioration. Nombre de caractères par wc -m
.
#coding:UTF8
k=""
for c in"*%s*"%raw_input():
i=" $*.02468BDFHJLNPRTVXZ%+-/13579ACEGIKMOQSUWY".find(c)*2
for j in"%05d%s"%tuple(map(ord,u"ಊҺூҺ姢ҺЈҺӎϴЈϴӐϲ刦ҺҺϴҼூ划ಊϴಊҺЈϴЈҼІ划ӎϴӎಊϴϴಌϲІூூҼІ刦ϴ勮ϲ刨ϲІҼӎҺ划勚ூ刔ூϲಌҺಊ划Ј勚І刔ІϲӐҺӎ姢ϴ媪ϲ姤ϲ"[i:i+2])):k+=["#"," ","###"," "][int(j)]
k+=" "
exec"print k;"*8
Lua, 318 caractères
z={"1358ACEHKMORUWY.","UVWXYZ-. $/+*","2369BCFILMPSVWZ ","0123456789$/%","0456DEFJNOPTXYZ*","ABCDEFGHIJ$+%","0789GHIJQRST-. *","KLMNOPQRST/+%","1247ABDGKLNQUVX-",""}i="*"..(...).."*"o=""for c in i:gfind(".")do for j=1,10 do o=o..((j%2==0 and" "or"#"):rep(z[j]:find(c,1,true)and 3 or 1))end end for j=1,8 do print(o)end
Je ne pense pas à gagner des questions de code de golf avec Lua, donc je ne me sens pas mal répondre à ma propre défi ici. Il utilisait aussi un codage différent, je pensais peut-être intéressant pour d'autres.
Autres observations
Après avoir examiné attentivement l'encodage, il semble que il peut y avoir un moyen de se passer de table de consultation, et calculer directement l'encodage du code à barres. Cependant, je trouve que mes tentatives pour construire les calculs ont plus de code que la table. (Cela peut ne pas être le cas dans d'autres langues.)
Après avoir divisé les caractères en groupes qui indiquaient où les larges barres et d'espaces étaient, j'ai vu des tendances intéressantes. Il semble qu'il n'y a qu'un seul grand espace pour 40 des caractères, avec les exceptions étant de $/+%
(ils ont chacun trois espaces.) Les 40 caractères étant répartis avec 10 dans chaque fente. Et, il y a deux barres larges pour les mêmes 40 caractères. Les larges barres semblent avoir un codage binaire avec la dernière barre étant un bit de parité. Les motifs de bits de la barre étant 1, 2, 3, 4, 5, 6, 8, 9, 10, 12 où les nombres ayant plus de 2 bits jeu étant évités.
1234567890ABCDEFGHIJKLMNOPQRSTUVWXYZ-._* 1 3 5 8 A C E H K M O R U W Y . 1010100100 23 6 9 BC F I LM P S VW Z _ 0110010010 456 0 DEF J NOP T XYZ * 0001110001 7890 GHIJ QRST -._* 0000001111 12 4 7 AB D G KL N Q UV X - 1101001000 --> Parity
Je suppose que c'est un défi pour un autre jour pour voir si les codes à barres peuvent être codées sans tables de consultation.
Je l'ai fait le code pour travailler avec le code 39 codes à barres sur les systèmes embarqués. Il existe deux types de codes, que je considère comme les 39 codes « réguliers » et les quatre « hurluberlus ». Les codes réguliers ont l'un des dix modes de largeurs de barre (deux trois large étroit), et l'un des quatre modèles de largeurs d'espace (une large trois étroite). Les excentriques ont cinq barres étroites et l'un des quatre modèles de largeurs de barre (trois larges une étroite). Pour rendre un code-barres avec le code compact, convertir le caractère en un certain nombre 0-39 (pour les codes normaux), ou 40, 50, 60, ou 70 pour « hurluberlus ». Ensuite DIVMOD 10. Le chiffre supérieur choisira l'un des huit modèles de largeurs d'espace; si le chiffre supérieur est de trois ou moins le chiffre inférieur sélectionne l'un des dix modes de largeurs de barre. Si le chiffre supérieur est 4-7, les cinq barres doivent être étroites.
Le code fonctionne très compacte en utilisant quelques petites tables de recherche. Comme les tables de consultation peuvent être représentés de manière compacte sous forme de chaînes dans le code source, les approches avec des tables de consultation plus grandes peuvent avoir plus court code source (bien que je pense que pour le code de golf taille du code source doit être pris en compte en octets en utilisant le codage le plus favorable, une approche avec une chaîne de personnages excentriques qui prendraient trois octets pour stocker en UTF-8 et deux octets pour UTF-16 doivent être soit « charge » 3 octets chacun des caractères excentriques, ou de deux octets chacun pour tous les caractères, selon donne un plus petit total). Une approche qui utilise une sélection de caractères farfelus qui correspondent entièrement dans une page de code sur un seul octet particulier doit être chargé d'un octet par caractère.
spam Spam Spam Spam lovely