Напишіть програму, яка перетворює кожен 17-й біт текстового файлу на 1


10

Ми з колегою працюємо над застарілим програмним забезпеченням, яке ми часом ненавидимо. Щоразу, коли ви запускаєте його, твердження про налагодження прилітають скрізь, і це ніколи не є гарантією того, що щось спрацює. Мотивація цього раунду кодового гольфу з’явилася від мого колеги, який сказав про наше програмне забезпечення наступне .

"Це як щоразу, коли ви запускаєте цю програму, ви погоджуєтесь з деякими умовами обслуговування, згідно з якими кожен 17-й біт на вашому жорсткому диску буде перетворений на 1"

Мета: Напишіть програму, яка зробить точну копію файлу і перетворить кожен 17-й біт текстового файлу в 1

  • Ви НЕ можете перетворювати КОЖНИЙ біт файлу на 1. тобто ваша програма повинна демонструвати деякий інтелект, що він націлений лише на кожен 17-й біт
  • Ви НЕ можете писати в оригінальний файл будь-якою формою чи формою
  • Переможець найменше уявлення програми в кінці місяця

Веселіться з цим! Ідіть!


7
1. Кожне питання потребує об'єктивного критерію виграшу. Більшість питань - це code-golfнайкоротший код у виграші байтів. Необхідна code-challengeчітко визначена система балів. 2. Перетворення кожного 18-го біта жорсткого диска в 1 можливо лише шляхом запису безпосередньо на диск. Це неможливо досягти, створюючи та / або змінюючи файли. 3. Це зробить весь привід непридатним, тому сумісне рішення буде руйнівним. Я не знаю, наскільки добре громада отримає запит на написання зловмисного програмного забезпечення ...
Dennis

2
Я би голосував за повторне відкриття цього питання, якби у мене було достатньо представників :/
Саммітч

3
@steveverrill Я зміню його на код гольфу, однак я збираюся змінити його з 18-го на 17-й біт, щоб зробити цікаві речі.
C. Tewalt

1
@matrixugly 17-й біт, звичайно, цікавіший. Майте на увазі, що це не дуже добре, щоб змінити правила таким чином, що недійсні відповіді (тому питання стають на затриманні, щоб уникнути публікації відповідей, які роблять питання неможливим виправити.) Однак існуюча відповідь не відповідає Так чи інакше не виконуються інші діючі правила, тому в цьому випадку це не є великою проблемою.
Рівень річки Св.

1
Як читається файл? stdin?
Міло,

Відповіді:


9

CJam, 22 байти

q256b2H#b1f|2H#b256b:c

Спробуйте в Інтернеті.

Зачіпає кожен 17-й біт, рахуючи з останнього.

Я використовував STDIN і STDOUT, оскільки CJam не має файлового вводу / виводу. Якщо це заборонено, програму можна загорнути в сценарій Bash вартістю 24 зайвих байта:

cjam <(echo q256b2H#b1f\|2H#b256b:c)<"$1">"$2"

Як це працює

q                      " Read from STDIN.                                                 ";
 256b                  " Convert to integer by considering the input a base 256 number.   ";
     2H#b              " Convert to array by considering the integer a base 2**17 number. ";
         1f|           " Set the LSB of every integer in the array element to 1.          ";
            2H#b       " Convert to integer by considering the array a base 2**17 number. ";
                256b   " Convert to array by considering the integer a base 256 number.   ";
                    :c " Turn character codes into characters.                            ";

1
+1, мені справді потрібно заглянути в CJam. Дивовижно, скільки затуманення ви можете потрапити на 22-байтний код, який досі служить цілі ...
Padarom

1
Молодці. Він перетворив "Візьміть кожен 17-й біт і перетворіть його на 1" в "" Tike vhe eöery 17th fiv і поверніть yt (до c 1 "
C. Tewalt

Чому це працює? Я не дотримуюся ..
Клавдіу,

1
Так, я не був впевнений, чи варто розміщувати його, але оскільки відповідь Perl в основному зробив те саме ... Обгортка Bash, щоб відповідати вимогам вводу / виводу файлів, збільшила кількість байтів до 46. Більше, ніж удвічі, але все ж найкоротша відповідь.
Денніс

1
@matrixugly вибачте! специфікація залишила ваш файл IO наміром трохи неоднозначним. я особисто не визнавав проблеми. не продовжувати харчуватися по суті пісочниці кодогольфа , але питання, що закриваються, і замішання цієї вимоги, можливо, можна було б уникнути. насолоджувався викликом незалежно
ardnew

6

Perl 59

заміщення регулярних виразів на бітових рядках:

$/=$\;$_=unpack"B*",<>;s|(.{16}).|${1}1|g;print pack"B*",$_

використання:

perl this.pl < infile.txt > outfile.txt

вимкнення можна змінити, перемикаючись між шаблонами bта Bв нихpack
ardnew

2

С, 125

Припускає великі цілі чисельні та 16-бітні числа .

Працює, застосовуючи побітові АБО на кожні два байти.

Вхідний файл є y, вихід - z.

unsigned a,b;main(c){void*f=fopen("y","r"),*g=fopen("z","w");while(b=fread(&c,1,2,f))c|=a,a?a/=2:(a=32768),fwrite(&c,1,b,g);}

Безумовно

// The commented out /* short */ may be used if int is not 16 bits, and short is. 
unsigned /* short */ a = 0,b;
main(/* short */ c){
    void *f = fopen("y", "r"), *g = fopen("z", "w");
    while(b = fread(&c, 1, 2, f)){
      // __builtin_bswap16 may be used if you are using GCC on a little-endian machine. 
      //c = __builtin_bswap16(c);
        c |= a;
        if(a) a >>= 1;
        else a = 32768;
      //c = __builtin_bswap16(c);
        fwrite(&c, 1, b, g);
    }
}

правила щодо цього питання були оновлені ...
Level River St

@steveverrill, і відповідь тепер оновлено відповідно
es1024

@Comintern Що має відбуватися за час, коли a стає 0:, 00000000 00000001 00000000 00000000 10000000 00000000таким чином, aу певних точках має бути нуль. Машина повинна використовувати великий ендіан (інакше ви мали б 00000000 10000000замість цього 10000000 00000000, що дало б неправильне значення).
es1024

Хрм ... Неважливо. Виймаючи c = __builtin_bswap16(c);виправили це.
Комінтерн

2

Python 2, 112 байт

b=open('i').read().encode('hex')
open('o','w').write(('%x'%(int('1'+b,16)|16**len(b)/131071))[1:].decode('hex'))

Це встановлює кожен 17-й біт-бит-ендіан, починаючи з 17-го з початку. Тут не використовуються бібліотеки. Він працює, перетворюючи вхідний файл у гігантське n-бітове ціле число та побітово ORing з 2**n/(2**17 - 1) == 0b10000000000000000100000000000000001….


1

С - 139

Читається з файлу під назвою "i", виводиться у файл під назвою "o".

c;main(){unsigned char b,m=1;void *i=fopen("i","r"),*o=fopen("o","w");for(;(b=fgetc(i))<129;fputc(b,o))((c+=8)%17<8)?b|=m=(m-1)?m/2:128:0;}

З розривами рядків:

c;main()
{
    unsigned char b,m=1;
    void *i=fopen("i","r"),*o=fopen("o","w");
    for(;(b=fgetc(i))<129;fputc(b,o))
        ((c+=8)%17<8)?b|=m=(m-1)?m/2:128:0;
}

Підраховує біти вхідних даних, а потім використовує плаваючу бітову маску для встановлення кожного сімнадцятого біта.


1

Ява - 247

Використовує a BitSetі простий цикл замість обробки / маскування байтів вручну. Звичайно, це Java, котельня - це половина програми, тому це не зовсім коротко.

Все-таки не останнє! : D

import java.util.*;import java.nio.file.*;class F{public static void main(String[]a)throws Exception{BitSet b=BitSet.valueOf(Files.readAllBytes(Paths.get(a[0])));for(int j=0;j<b.size();b.set(j),j+=17);Files.write(Paths.get("o"),b.toByteArray());}}

Версія без прокрутки:

import java.util.*;
import java.nio.file.*;
class F{
    public static void main(String[]a)throws Exception{
        BitSet b=BitSet.valueOf(Files.readAllBytes(Paths.get(a[0])));
        for(int j=0;j<b.size();b.set(j),j+=17);
        Files.write(Paths.get("o"),b.toByteArray());
    }
}

1

Пітон - 98 байт

Читай від i, пиши о. Використовується бібліотека бітрейра https://pypi.python.org/pypi/bitarray

from bitarray import*;a=bitarray();a.fromfile(open('i','rb'));a[::17]=1;a.tofile(open('o','wb'))

неозорий

from bitarray import *
a=bitarray()
a.fromfile(open('i','rb'))
a[::17]=1
a.tofile(open('o','wb'))

Хіба це не повинно бути a[::17]=1?
підземниймонорельс

Також я вважаю, що ви можете зберегти байт за допомогою from bitarray import*та a=bitarray().
підземниймонорельс

0

Кобра - 308

use System.Text.RegularExpressions
class P
    def main
        t,b='',File.readAllBytes('x')
        for n,i in b.numbered,for l in 8,b[n]=if(l,b[n],0)+if(Regex.replace(t+='00000000'[(j=Convert.toString(i,2)).length:]+j,'.{17}',do(m as Match)='[m]'[:-1]+'1')[n*=8:n+8][7-l]<c'1',0,2**l)to uint8
        File.writeAllBytes('y',b)

Кожного разу, коли я роблю один із таких викликів, що "маніпулюють окремими шматочками чогось", я хочу, щоб у Cobra чи стандартної бібліотеки .NET був binary string => integerконвертер.


0

Javascript (+ HTML5), 282

Напевно, не найкоротший, але це зручно для користувачів: D

Це перехресний веб-переглядач, але, схоже, що chrome - це єдиний, який дозволяє це, коли html-файл - це локальний файл (= доступ із file://...). Для інших браузерів вам потрібно розмістити його на веб-сервері.

Вихідний файл слід зберегти у каталозі завантажень за замовчуванням, можливо, із запитом на файл (залежно від конфігурації).

<input type=file onchange="r=new FileReader();r.onloadend=function(){w=window;a=new Uint8Array(r.result);for(i=17;i<a.length*8;i+=17)a[i/8>>0]|=1<<8-i%8;w.location.replace(w.URL.createObjectURL(new Blob([a],{type:'application/octet-binary'})));};r.readAsArrayBuffer(this.files[0])">

Негольована версія:

<input type=file onchange="
    var reader = new FileReader();
    reader.onloadend = function() {
        var arr = new Uint8Array(reader.result);
        for(var i = 17 ; i < arr.length * 8 ; i += 17) {
            arr[Math.floor(i / 8)] |= 1 << (8 - (i % 8));
        }
        window.location.replace(
            window.URL.createObjectURL(
                new Blob([arr], {type: 'application/octet-binary'})
            )
        );
    };
    reader.readAsArrayBuffer(this.files[0]);
">

0

Python 3 - 187 байт


Читає з iі пише в o.

Код:

o=open;j="".join;f=list(j(format(x,"08b")for x in o("i","rb").read()))
f[16::17]="1"*(len(f)//17)
with o("o","wb") as f2:f2.write(bytes(int(j(f[i*8:(i+1)*8]),2)for i in range(len(f)//8)))

Безголівки:

# read file and convert to binary string e.g. "101010010101010101"
f = list("".join(format(x, "08b") for x in open("in.txt", "rb").read()))
# set every 17th bit to 1
f[16::17] = "1" * (len(f)//17)
with open("out.txt","wb") as f2:
    data = []
    for i in range(len(f)//8)): # for each byte
        byte = "".join(f[i*8:(i+1)*8] # get each byte
        data.append(int(byte),2) # convert to int
    f2.write(bytes(data)) # convert to byte string and write

-1

Пітон 3 - 103 символів

Перейдіть fдо шляху файлу, який ви хочете прочитати, і oдо шляху файлу, в який ви хочете написати.

l=open;t=list(l(f,'r').read())
for i in range(len(t)):
 if i%18==0:t[i]='1'
l(o,'w').write(''.join(t)) 

6
Це кожен 17-й біт, а не байт.
matsjoyce

1
Також це 17-е, а не 18-те.
Денніс
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.