Fammi un po 'di moji


26

Data una stringa, un elenco di caratteri, un flusso di byte, una sequenza ... che è sia UTF-8 valido che Windows-1252 valido (la maggior parte delle lingue probabilmente vorrà prendere una normale stringa UTF-8), convertirla da (ovvero, fingere che sia ) Da Windows 1252 a UTF-8 .

Esempio da seguire

La stringa UTF-8
I            UTF-8
è rappresentata come byte
49 20E2 99 A520 55 54 46 2D 38
questi valori di byte nella tabella Windows-1252 ci fornisce gli equivalenti Unicode
49 20 E2 2122 A5 20 55 54 46 2D 38
che vengono visualizzati come
I ⥠UTF-8

Esempi

£Â£

£Â£

£Â£

I ♥ UTF-8I ♥ UTF-8

árvíztűrő tükörfúrógépárvÃztűrÅ‘ tükörfúrógép


9
@ user202729 Vedi il link "convertilo". È un gioco di parole.
Erik the Outgolfer,

5
Per comodità: il set di caratteri di Windows 1252 è uguale a Unicode, tranne in 0x80..0x9F, dove si trovano i caratteri € ‚ƒ„…†‡ˆ‰Š‹Œ Ž ‘’“”•–—˜™š›œ žŸ. (spazio = non utilizzato)
user202729

3
@ user202729 Uh, non sono sicuro di quello che stavi cercando di dire, ma questo non è molto vicino all'essere vero. Unicode ha milioni di caratteri, Windows-1252 solo 256.
David Conrad,

1
@DavidConrad, "Unicode ha milioni di caratteri" è esagerato. Unicode definisce 1.114.112 punti di codice. Di questi 136.690 punti di codice sono attualmente utilizzati.
Wernfried Domscheit,

1
@Wernfried il punto sta confrontando quello con un set di caratteri di 256 caratteri.
David Conrad,

Risposte:



19

Java 8, 72 66 36 25 byte

s->new String(s,"cp1252")

Provalo online.

s->  // Method with byte-array (UTF-8 by default) as parameter and String return-type
  new String(s,"cp1252")
     //  Pretend this UTF-8 input is (and convert it to) Windows-1252,
     //  and return it as UTF-8 String (by default) as well

cp1252è un alias per Windows-1252. Questo alias cp1252è il nome canonico per le API java.ioe java.lang, mentre il nome completo Windows-1252è il nome canonico per l' java.nioAPI. Vedi qui per un elenco completo delle codifiche Java supportate , dove vorremmo sempre usare il più corto dei due per codegolfing.


13
Codice vincente Java golf‽ Non può essere giusto.
Adám,

1
@Adám Hehe, in realtà sono piacevolmente sorpreso anche di vedere tutte queste risposte più lunghe. ;) Ma sono abbastanza sicuro che Jelly, 05AB1E, ecc. Mi batterà abbastanza presto.
Kevin Cruijssen,

1
Ne dubito. Probabilmente non hanno tabelle di traduzione integrate. Dyalog APL lo fa ...
Adám,

"Nome canonico per l' java.nioAPI": P
ASCII il

8

R 3.5.0 o superiore, 32 20 byte

scan(,"",e="latin1")

Provalo online!

Stranamente abbreviato per una sfida a in R ... grazie a JayCe per giocare a golf con altri 12 byte!

scanopzionalmente accetta un encodingargomento per impostare la codifica della stringa di input. latin1corrisponde a, secondo la documentazione diEncoding

Vi è una certa ambiguità su cosa si intende per locale "Latin-1", poiché alcuni sistemi operativi (in particolare Windows) fanno uso delle posizioni dei caratteri utilizzate per controllare i caratteri nel set di caratteri ISO 8859-1. Il modo in cui tali caratteri vengono interpretati dipende dal sistema, ma a partire dalla R 3.5.0, se possibile, vengono interpretati secondo la tabella codici 1252 di Windows (che Microsoft chiama "Windows Latin 1 (ANSI)") durante la conversione in UTF-8.


3
Ho seguito il link alla documentazione di Encoding... e ho appreso che scanha anche un encodingargomento O_O ... 20 byte
JayCe

@JayCe whoda lo ha provato! Molto bella!
Giuseppe,

6

Python 2 , 40 38 byte

-2 byte grazie a Erik the Outgolfer .

lambda s:s.decode('1252').encode('u8')

Provalo online!

u8 è un alias per utf-8.


Forse potresti "imbrogliare" un po 'con questo: input().decode(...).encode(...):) anche io penso che potresti essere in grado di usare un po' di codifica della console di Windows in PowerShell (ma non ne sono del tutto sicuro).
KeyWeeUsr,


@KeyWeeUsr il problema con il tuo suggerimento è che in realtà non viene prodotto nulla, al contrario della risposta che hai collegato. R produce il valore dell'espressione nuda mentre non lo fa.
Ovs,

4

Python 3 , 38 36 34 byte

lambda s:s.encode().decode('1252')

Provalo online!

nota: dopo aver svolto una funzione funzionante ho usato la risposta python2 di ovs answer per conoscere i campi header e footer per tio, quindi header e footer sono gli stessi

edit: L'ho tagliato un po 'grazie a python3 che è andato in default su utf8 e un suggerimento dall'invio di ovs :)


3

JavaScript, 64 byte

x=>new TextDecoder('cp1252').decode(new TextEncoder().encode(x))

Anche più a lungo della risposta Java. Così triste. :(



3

C #, 81 byte

using e=System.Text.Encoding;s=>e.GetEncoding(1252).GetString(e.UTF8.GetBytes(s))

Provalo online!

Grazie a Schmalls per 3 byte


Può essere using e=System.Text.Encoding;s=>e.GetEncoding(1252).GetString(e.UTF8.GetBytes(s))arrivare a 81?
Schmalls,

@Schmalls Sembra sì, grazie!
Mego,

2

180 byte, codice macchina (16 bit x86)

Ho notato che la maggior parte delle risposte usa la codifica / decodifica incorporata (che credo sia perfettamente soddisfacente), ma ho pensato che continuerò la mia ricerca a 16 bit .

Come con i precedenti, questo è stato fatto senza compilatore usando principalmente hexeditor HT e hexplorer di ICY .

00000000: eb40 ac20 0000 1a20 9201 1e20 2620 2020  .@. ... ... &                     
00000010: 2120 c602 3020 6001 3920 5201 0000 7d01  ! ..0 `.9 R...}.                  
00000020: 0000 0000 1820 1920 1c20 1d20 2220 1320  ..... . . . " .                   
00000030: 1420 dc02 2221 6101 3a20 5301 0000 7e01  . .."!a.: S...~.                  
00000040: 7801 89f7 4646 89fa 89d9 4143 4bb4 3fcd  x...FF....ACK.?.                  
00000050: 2185 c074 288a 053c 8073 05e8 1700 ebec  !..t(..<.s......                  
00000060: 3ca0 721a d440 0d80 c050 86c4 e806 0058  <.r..@...P.....X                  
00000070: e802 00eb d7b4 4088 05b3 01cd 21c3 2c80  ......@.....!.,.                  
00000080: d0e0 89c3 8b00 89cb 85c0 74c0 3dff 0773  ..........t.=..s                  
00000090: 08c1 c002 c0e8 02eb cd50 c1e8 0c0c e0e8  .........P......                  
000000a0: d3ff 5825 ff0f c1c0 02c0 e802 0d80 8050  ..X%...........P                  
000000b0: 86c4 ebb8                                ....                              

bake.com <input.txt> out.dat

Dissezione

L'implementazione è piuttosto semplice, anche se non ho pensato molto a fluire in anticipo quindi ci sono ALCUNI spaghetti.

Mescolerò un po 'l'ordine, per rendere più facile seguire ...

0000 eb40               jmp         0x42

Passa sulla tabella che mappa i caratteri> = 0x80 <0xa0, ai codici unicode.

data db ACh,20h, 00h,00h, 1Ah,20h, ...

Quelli non validi sono codificati come 0, non sono associati a nulla

0075 b440               mov         ah, 0x40   
0077 8805               mov         [di], al   
0079 b301               mov         bl, 0x1    
007b cd21               int         0x21       
007d c3                 ret                    

La funzione di supporto utilizzata per stampare il carattere alverrà richiamata alcune volte.

0042 89f7               mov         di, si     
0044 46                 inc         si         
0045 46                 inc         si         
0046 89fa               mov         dx, di     
0048 89d9               mov         cx, bx     
004a 41                 inc         cx         
004b 43                 inc         bx         

Preparare i registri. I dati verranno letti in 0x100, si faccia siriferimento alla tabella di traduzione sopra.

004c 4b                 dec         bx         
004d b43f               mov         ah, 0x3f   
004f cd21               int         0x21       
0051 85c0               test        ax, ax     
0053 7428               jz          0x7d       

Leggi il carattere da stdin, passa a 0x7d se EOF.

Nota a margine: Questo in realtà è un piccolo (ma abbastanza noto) trucco, 0x7D contiene ret, questo farà sì che pop sp, spnei punti dall'inizio alla fine di un segmento, c'è 00 00lì, ecs:0 in DOS contiene CD 20, che provoca la dell'applicazione.

0055 8a05               mov         al, [di]   
0057 3c80               cmp         al, 0x80   
0059 7305               jnc         0x60       
005b e81700             call        0x75       
005e ebec               jmp         0x4c       

Se char è <0x80, stampalo e vai all'inizio del ciclo (poiché la funzione di supporto sta impostando BX su 1 - stdout, i salti andranno a dec bx )

0060 3ca0               cmp         al, 0xa0   
0062 721a               jc          0x7e       
0064 d440               aam         0x40       
0066 0d80c0             or          ax, c080   
0069 50                 push        ax         
006a 86c4               xchg        ah, al     
006c e80600             call        0x75       
006f 58                 pop         ax         
0070 e80200             call        0x75       
0073 ebd7               jmp         0x4c       

Questa parte tratta i caratteri> = 0xa0, divide il codice ASCII in due bit "alti" e 6 bit "bassi" e applica la maschera utf-8 c080 per due byte, quindi stampa entrambi

007e 2c80               sub         al, 0x80   
0080 d0e0               shl         al, 0x1    
0082 89c3               mov         bx, ax     
0084 8b00               mov         ax, [bx+si]
0086 89cb               mov         bx, cx     
0088 85c0               test        ax, ax     
008a 74c0               jz          0x4c       
008c 3dff07             cmp         ax, 07ff   
008f 7308               jnc         0x99       
0091 c1c002             rol         ax, 0x2    
0094 c0e802             shr         al, 0x2    
0097 ebcd               jmp         0x66       

Questa parte tratta i caratteri> = 0x80 <0xa0, trova il codice utf-8 corretto nella tabella in alto, se il codice è uguale a 0, salta all'inizio, se è inferiore a 0x7ff (ergo: si adatta a due byte UTF-8) , basta regolare il valore e riutilizzare il codice precedente su 0x166.

0099 50                 push        ax         
009a c1e80c             shr         ax, 0xc    
009d 0ce0               or          al, e0     
009f e8d3ff             call        0x75       
00a2 58                 pop         ax         
00a3 25ff0f             and         ax, 0fff   
00a6 c1c002             rol         ax, 0x2    
00a9 c0e802             shr         al, 0x2    
00ac 0d8080             or          ax, 8080   
00af 50                 push        ax         
00b0 86c4               xchg        ah, al     
00b2 ebb8               jmp         0x6c       

La parte finale, si occupa di codici superiori a 0x7FF, rilascia 12 bit bassi, applica 0xE0 (vedere la descrizione della codifica UTF-8 per riferimento) e stampa, regola 12 bit inferiori e applica la maschera 8080 e riutilizza nuovamente la parte che sputa due caratteri .


1

PHP + mbstring , 63 49 byte

<?=mb_convert_encoding($argv[1],'UTF8','CP1252');

Non funziona su TIO a causa della mancanza di mbstring. Il terzo parametro forza mbstring ad interpretare la stringa come codificato Windows-1252

-14 byte grazie a Ismael Miguel


<?=mb_convert_encoding($argv[1],'UTF8','CP1252');<- ancora più breve!
Ismael Miguel,

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.