Испечь мне моджи

26

Учитывая строку, список символов, поток байтов, последовательность ... которая является допустимой UTF-8 и действительной Windows-1252 (большинство языков, вероятно, захотят взять обычную строку UTF-8), преобразуйте ее из (то есть представьте, что это ) Windows-1252 для UTF-8 .

Проходной пример

Строка UTF-8
I            UTF-8
представляется в виде байтов,
49 20E2 99 A520 55 54 46 2D 38
эти значения байтов в таблице Windows-1252 дают нам эквиваленты Unicode,
49 20 E2 2122 A5 20 55 54 46 2D 38
которые отображаются как
I ⥠UTF-8

Примеры

£Â£

£Â£

£Â£

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 Смотрите ссылку "конвертировать". Это игра слов.
Эрик Outgolfer
5
Для удобства: набор символов Windows 1252 аналогичен Unicode, за исключением 0x80..0x9F, где символы € ‚ƒ„…†‡ˆ‰Š‹Œ Ž ‘’“”•–—˜™š›œ žŸ. (пробел = не используется)
user202729
3
@ user202729 Э-э, я не уверен в том, что вы пытались сказать, но это далеко не так. В Юникоде миллионы символов, в Windows-1252 только 256.
Дэвид Конрад,
1
@DavidConrad, «Юникод имеет миллионы символов» преувеличено. Юникод определяет 1,114,112 кодовых точек. Из этого 136 690 кодовых точек в настоящее время используются.
Вернфрид Домшайт
1
@Wernfried суть в том, что он сравнивается с набором символов из 256 символов.
Дэвид Конрад

Ответы:

23

Баш, 14 байтов

iconv -fCP1252

Попробуйте онлайн!

Дверная ручка
источник
проголосовал, но если я не ошибаюсь, это предполагает, что кодировка системы - utf-8
GiM
19

Java 8, 72 66 36 25 байт

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

Попробуйте онлайн.

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это псевдоним для Windows-1252. Этот псевдоним cp1252является каноническим именем для java.ioи java.langAPI - интерфейсов, в то время как полное имя Windows-1252является каноническим именем для java.nioAPI. Смотрите здесь полный список поддерживаемых кодировок Java , где мы всегда хотели бы использовать самое короткое из двух для кодгольфинга.

Кевин Круйссен
источник
13
Java, выигрышный код в гольф‽ Это не может быть правильно.
Адам
1
@ Adám Хе-хе, я тоже приятно удивлен, увидев все эти более длинные ответы. ;) Но я почти уверен, что Jelly, 05AB1E и т. Д. Скоро победят меня.
Кевин Круйссен
1
Сомневаюсь. Они, вероятно, не имеют встроенных таблиц перевода. Dyalog APL делает хотя ...
Adám
«Каноническое имя для java.nioAPI»: P
только ASCII,
8

R 3.5.0 или выше, 32 20 байт

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

Попробуйте онлайн!

Как ни странно мало для вызова в R ... благодаря Jayce для игры в гольф вниз еще 12 байт!

scanопционально принимает encodingаргумент для установки кодировки входной строки. latin1соответствует, согласно документацииEncoding

Существует некоторая двусмысленность в отношении того, что подразумевается под языком «Latin-1», поскольку некоторые ОС (особенно Windows) используют позиции символов, используемые для управляющих символов в наборе символов ISO 8859-1. То, как такие символы интерпретируются, зависит от системы, но начиная с R 3.5.0 они, если возможно, интерпретируются согласно кодовой странице Windows 1252 (которую Microsoft называет «Windows Latin 1 (ANSI)») при преобразовании, например, в UTF-8.

Giuseppe
источник
3
Я перешел по ссылке на документацию Encoding... и узнал, что scanтакже имеет encodingаргумент O_O ... 20 байт
JayCe
@ JayCe, чёрт возьми! Очень хорошо!
Джузеппе
6

Python 2 , 40 38 байт

-2 байта благодаря Эрику Аутгольферу .

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

Попробуйте онлайн!

u8 это псевдоним для utf-8.

овс
источник
Возможно, вы могли бы немного «обмануть» это: input().decode(...).encode(...):) также я думаю, что вы могли бы использовать некоторую кодировку консоли Windows, если в PowerShell (но я совершенно не уверен в этом).
KeyWeeUsr
@KeyWeeUsr проблема с вашим предложением в том, что он на самом деле ничего не выводит, в отличие от ответа, который вы связали. R выводит значение голого выражения, а нет.
Ов
4

Python 3 , 38 36 34 байта

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

Попробуйте онлайн!

примечание: после того, как у меня появилась рабочая функция, я использовал ответ ovs's python2 answer, чтобы узнать о полях верхнего и нижнего колонтитула для tio, поэтому верхний и нижний колонтитулы совпадают

редактирование: немного обрезано благодаря python3 по умолчанию utf8 и совет от ovs :)

GammaGames
источник
3

JavaScript, 64 байта

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

Даже дольше, чем ответ Java. Очень грустно. :(

ТТГ
источник
3

C #, 81 байт

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

Попробуйте онлайн!

Спасибо Schmalls за 3 байта

Mego
источник
Может ли это быть using e=System.Text.Encoding;s=>e.GetEncoding(1252).GetString(e.UTF8.GetBytes(s))до 81?
Schmalls
@Schmalls Похоже, да, спасибо!
Мего
2

180 байт, машинный код (16-битный x86)

Я заметил, что в большинстве ответов используется встроенное кодирование / декодирование (что, я считаю, прекрасно), но я решил продолжить 16-битный квест .

Как и предыдущие, это было сделано без компилятора с использованием в основном HT двоичный редактор и hexplorer 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

рассечение

Реализация довольно прямолинейна, хотя я не слишком задумывался над тем, чтобы продвигаться вперед, поэтому там есть НЕКОТОРЫЕ спагетти.

Я немного смешаю порядок, чтобы было легче следовать ...

0000 eb40               jmp         0x42

Пропустите таблицу, которая отображает символы> = 0x80 <0xa0, в коды Unicode.

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

Неверные из них кодируются как 0, они ни к чему не привязаны

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

Вспомогательная функция, используемая для печати char al, будет вызываться несколько раз.

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         

Подготовьте регистры. Данные будут считаны в 0x100, пусть siуказывается в таблице перевода выше.

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

Чтение символа из стандартного ввода, переход к 0x7d, если EOF.

Sidenote: Это на самом деле небольшой (но довольно хорошо известный) трюк, 0x7d содержит ret, это приведет к тому pop sp, что spв начальных точках до конца сегмента есть 00 00, а cs:0в DOS содержит CD 20, что приводит к выходу приложения.

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

Если char <0x80, просто распечатайте его и перейдите к началу цикла (поскольку вспомогательная функция устанавливает BX в 1 - stdout, переходы переходят в 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       

Эта часть имеет дело с символами> = 0xa0, разбивает код ascii на «старшие» два бита и «младшие» 6 бит и применяет маску utf-8 c080 для двух байтов, а затем печатает оба из них

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       

Эта часть имеет дело с символами> = 0x80 <0xa0, она находит правильный код utf-8 в таблице вверху, если код равен 0, просто перейдите к началу, если он меньше 0x7ff (ergo: подходит для двух байтов UTF-8) просто измените значение и повторно используйте предыдущий код в 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       

В заключительной части рассматриваются коды выше 0x7FF, отбрасываются младшие 12 битов, применяются 0xE0 ( для справки см. Описание кодирования UTF-8 ) и распечатывается его, корректируются младшие 12 битов, применяется маска 8080 и снова используется часть, которая выплевывает два символа. ,

GiM
источник
1

PHP + mbstring , 63 49 байт

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

Он не работает на TIO из-за отсутствия mbstring. Третий параметр заставляет mbstring интерпретировать строку в кодировке Windows-1252.

-14 байт благодаря Исмаилу Мигелю

Сефа
источник
<?=mb_convert_encoding($argv[1],'UTF8','CP1252');<- еще короче!
Исмаэль Мигель