Більше, ніж менше, ніж щось рибне


45

Враховуючи довжину N рядків менших та більших за знаки ( <, >), вставте цілі числа від 0 до N на початку та в кінці та між кожною парою знаків таким чином, щоб усі нерівності були задоволені. Виведіть отриманий рядок. Якщо є кілька дійсних виходів, виведіть будь-який (і лише один) з них.

Наприклад

<<><><<

має 7 символів, тому всі цифри від 0 до 7 включно потрібно вставити. Дійсний вихід

2<3<4>1<5>0<6<7

тому що всі нерівності беруться одна за одною

2<3
3<4
4>1
1<5
5>0
0<6
6<7

правдиві.

За бажанням на виході можуть бути пробіли, що оточують знаки, наприклад 2 < 3 < 4 > 1 < 5 > 0 < 6 < 7.

Виграє найкоротший код у байтах.

Випробування

Перший рядок після порожнього рядка - це вхід, а наступний рядок - кожен дійсний приклад виводу.

[empty string]
0

<
0<1

>
1>0

<<
0<1<2

<>
1<2>0

><
1>0<2
2>0<1

>>
2>1>0

<<<
0<1<2<3

><>
1>0<3>2

>><
3>2>0<1
3>1>0<2
2>1>0<3

>>>
3>2>1>0

>>><<<
3>2>1>0<4<5<6
6>3>1>0<2<4<5
4>2>1>0<3<5<6
4>3>1>0<2<5<6

<<><><<
2<3<4>1<5>0<6<7

>><><>>
7>6>0<5>1<4>3>2

<<<<<<<<<<<<<<
0<1<2<3<4<5<6<7<8<9<10<11<12<13<14

>><<<<><>><><<
6>5>4<7<8<9<10>3<11>2>1<12>0<13<14
14>5>4<7<8<9<10>3<11>2>1<12>0<13<6

4
Чи завжди буде дійсний вихід?
mbomb007

3
@ mbomb007 Так. Завжди є хоча б один.
Захоплення Кальвіна

23
Я хочу бачити, щоб хтось програмував це в <<>! Це було б приголомшливо (а гадаю, іронічно?)
Soren

Це було дійсно весело, але просто виклик, дякую оп
Shaun Wild

Відповіді:


29

Сітківка , 20 байт

Кількість байтів передбачає кодування ISO 8859-1.


$.'
S`>
%O#`\d+
¶
>

Спробуйте в Інтернеті! (Перший рядок увімкнює тестовий набір, відокремлений підведенням даних.)

Пояснення

Простий спосіб , щоб знайти дійсну перестановку, щоб почати шляхом вставки цифри від 0до Nв порядку, а потім у зворотному число , що оточує кожну подстроку >с. Візьмемо <><<>>><<як приклад:

0<1>2<3<4>5>6>7<8<9
  ---   -------      these sections are wrong, so we reverse them
0<2>1<3<7>6>5>4<8<9

Обидва ці завдання у Retina досить прості, хоча все, з чим ми справді можемо працювати, - це рядки. Ми можемо зберегти додатковий байт, вставивши числа Nзнизу до 0та замінивши <замість них розділи , але принцип той самий.

Етап 1: Заміна


$.'

Почнемо, вставляючи довжину $'(суфікс, тобто все після матчу) у кожну можливу позицію на вході. Це вставляє цифри Nзнизу до 0.

2 етап: Спліт

S`>

Ми розділили вхід навколо >на окремі рядки, тому кожен рядок є або індивідуальним номером, або списком чисел, з якими поєднано <.

3 етап: Сортування

%O#`\d+

У кожному рядку ( %) сортуємо ( O) числа ( \d#) за їх числовим значенням ( #). Оскільки ми вставили число у зворотному числовому порядку, це повертає їх.

Етап 4: Заміна

¶
>

Ми знову перетворюємо канали >ліній, щоб об'єднати все в один рядок. Це воно.

Як зауваження, я мав намір додати спосіб подання заявки %на інші роздільники, ніж лінійні канали Якби я вже робив це, це подання було б 14 байтів, тому що тоді три останні етапи були б зведені до одного:

%'>O#`\d+

Як це як один вісім мого розміру? Хороша робота.
ThreeFx

@ThreeFx Тому що я не використовую грубу силу. ;) Пояснення надходить за хвилину.
Мартін Ендер

22

> <> , 46 43 35 + 4 для  -s== 39 байт

0&l?!v:3%?\&:n1+$o!
+nf0.>&n; >l&:@

Це реалізація алгоритму xnor у> <>.

Він займає вхідний рядок на стеку ( -sпрапор із стандартним перекладачем).

Ви можете спробувати це на онлайн-перекладачі .


2
> <> здається, що мова підходить для цього завдання.
anaximander

21

> <> , 26 + 4 = 30 байт

l22pirv
1+$2po>:3%::2g:n$-

Спробуйте в Інтернеті! +4 байти для -s=прапора - якщо просто -sгаразд (це означатиме, що прапор потрібно буде повністю скинути для порожнього введення), то це буде +3.

Передбачається, що вхід STDIN порожній, так що iутворюється -1 (що це робиться на EOF). Програма помиляється, намагаючись роздрукувати цей -1 як графік.

Використовує підхід max-of-nums-far-for- >, min-of-nums-so-far-for- <.

[Setup]
l22p         Place (length of stack) = (length of input) into position (2, 2) of
             the codebox. Codebox values are initialised to 0, so (0, 2) will
             contain the other value we need.
i            Push -1 due to EOF so that we error out later
r            Reverse the stack
v            Move down to the next line
>            Change IP direction to rightward

[Loop]
:3%          Take code point of '<' or '>' mod 3, giving 0 or 2 respectively
             (call this value c)
:            Duplicate
:2g          Fetch the value v at (c, 2)
:n           Output it as a number
$-1+         Calculate v-c+1 to update v
$2p          Place the updated value into (c, 2)
o            Output the '<' or '>' as a char (or error out here outputting -1)

Програма, яка виходить чисто і не припускає STDIN, - це 4 зайві байти:

l22p0rv
p:?!;o>:3%::2g:n$-1+$2


11

Perl, 29 байт

Включає +2 для -lp

Виконати з введенням на STDIN, наприклад

order.pl <<< "<<><><<"

Вихід:

0<1<7>2<6>3<4<5

order.pl:

#!/usr/bin/perl -lp
s%%/\G</?$a++:y///c-$b++%eg

Пояснення

Майте два лічильника, макс починаючи з довжини рядка, хв починаючи з 0. Потім на кожному кордоні (включаючи початок і кінець рядка), якщо він знаходиться безпосередньо перед тим, як <поставити мінімум там, і збільшити на 1, інакше поставте туди максимум і зменшіть на 1 (в кінці рядка не має значення, який лічильник ви берете, оскільки вони обидва однакові)


s{}{/\G/...}Я ніколи цього не бачив, це геніально.
примо

10

Python 2, 67 байт

f=lambda s,i=0:s and`i+len(s)*(s>'=')`+s[0]+f(s[1:],i+(s<'>'))or`i`

Рекурсивна функція. Задовільно задовольняє кожного оператора, ставлячи найменше невикористане значення xдля x<та найбільше для x>. Найменше невикористане значення зберігається iта оновлюється, а найбільше невикористане значення виводиться із iта довжини, що залишилася.


1
Я думаю, ви могли б зробити (s>'=')замість того, (s>='>')щоб зберегти байт?
mathmandan

@mathmandan Дякую! Дивно, що <і >не є послідовними кодовими точками.
xnor

Домовились! Але я думаю, я бачу, як було б сенс мати =між собою <і >.
mathmandan

8

Пітон 2, 163 137 байт

from random import*
def f(v):l=len(v)+1;N=''.join(sum(zip(sample(map(str,range(l)),l),v+' '),()));return N if eval(N)or len(v)<1else f(v)

Перемішуйте числа, поки оператор не дорівнює True.

Спробуй це.


Це, очевидно, найрозумніша з усіх відповідей.
moopet

7

APL, 33 байти

⍞←(S,⊂''),.,⍨-1-⍋⍋+\0,1-2×'>'=S←⍞

⍋⍋ незвично корисний.

Пояснення

⍞←(S,⊂''),.,⍨-1-⍋⍋+\0,1-2×'>'=S←⍞
                                   ⍞ read a string from stdin      '<<><><<'
                                 S←   store it in variable S
                             '>'=     test each character for eq.   0 0 1 0 1 0 0
                         1-2×         1-2×0 = 1, 1-2×1 = ¯1         1 1 ¯1 1 ¯1 1 1
                                      (thus, 1 if < else ¯1)
                       0,             concatenate 0 to the vector   0 1 1 ¯1 1 ¯1 1 1
                     +\               calculate its running sum     0 1 2 1 2 1 2 3
                   ⍋                 create a vector of indices    1 2 4 6 3 5 7 8
                                      that sort the vector in
                                      ascending order
                 ⍋                   do it again: the compound ⍋⍋ 1 2 5 3 6 4 7 8
                                      maps a vector V to another
                                      vector V', one permutation of
                                      the set of the indices of V,
                                      such that
                                            V > V  => V' > V'.
                                             i   j     i    j
                                      due to this property, V and V'
                                      get sorted in the same way:
                                          ⍋V = ⍋V' = ⍋⍋⍋V.
              -1-                     decrement by one              0 1 4 2 5 3 6 7
      ⊂''                            void character vector         ⊂''
    S,                                concatenate input string     '<<><><<' ⊂''
   (     ),.,⍨                       first concatenate each        0 '<' 1 '<' 4 '>' 2 \
                                     element of the result vector  '<' 5 '>' 3 '<' 6 '<' \
                                     with the cordisponding        7 ⊂''
                                     element in the input string,
                                     then concatenate each result
⍞←                                  write to stdout

3
Що роблять ялинки ( ⍋⍋)?
Conor O'Brien

є оцінка, яка повертає показники в упорядкованому порядку. Виконуючи це двічі, ви отримуєте 1там, де було найменше число, 2де було наступне найменше число, і т.д.
Цвей

@ ConorO'Brien відредаговано з коротким поясненням.
Оберон

Так, дуже короткий ._.
Conor O'Brien

7

JavaScript (ES6), 74 56 байт

s=>s.replace(/./g,c=>(c<'>'?j++:l--)+c,j=0,l=s.length)+j

Починається з набору чисел 0...N. На кожному етапі просто береться найбільше ( l) або найменше ( j) з решти цифр; наступне число за визначенням повинно бути меншим або більшим за це. Редагувати: Збережено величезні 18 байт завдяки @Arnauld.


3
Ви можете використовувати replace? Можливоs=>s.replace(/./g,c=>(c<'>'?j++:l--)+c,j=0,l=s.length)+j
Арнольд

@Arnauld ... і я подумав, що в мене все добре робиться в гольф, коли моя перша спроба (яку не можна було замінити на replace) до 74 байт ...
Ніл

5

Pyth - 19 байт

Ура за ланцюжок порівняння!

!QZhv#ms.idQ.p`Mhl

Не працює в Інтернеті, тому що eval безпеки.


4

2 придатних , 20 байт

gUvy'<Qi¾¼ëXD<U}y}XJ

Пояснення

gU                     # store input length in variable X
  v              }     # for each char in input
   y'<Qi               # if current char is "<"
        ¾¼             # push counter (initialized as 0), increase counter
          ëXD<U}       # else, push X and decrease value in variable X
                y      # push current char
                  XJ   # push the final number and join the stack

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

Для N <10 це могло бути 14 байт:

ÎvyN>}J'<¡í'<ý

4

C #, 102 99 байт

string f(string s){int i=0,j=s.Length;var r="";foreach(var c in s)r=r+(c<61?i++:j--)+c;return r+i;}

Безголівки:

string f(string s)
{
    int i = 0, j = s.Length;    // Used to track the lowest and highest unused number.
    var r = "";                 // Start with the empty string.

    foreach (var c in s)        // For each character in the input string:
        r = r +                 // Append to the result:
            (c < 61             // If the current character is '<':
                ? i++           // Insert the lowest unused number,
                : j--)          // otherwise, insert the highest unused number.
            + c;                // And append the current character.

    return r + i;               // Return the result with the last unused number appended.
}

Я втомився, тому я міг щось пропустити, але чи не змінивши r = r +частину на складене завдання, врятуйте пару байтів?
Carcigenicate

2
Ні - r+частина праворуч повідомляє компілятору, що вся справа є рядком, тому використовується рядкове подання c. Якби я використовував r+=, ?:частина буде оцінювати до int, порядкове значення cдодається до цього, і лише тоді воно буде перетворене на його рядкове подання.
Сцефео

4

Java 8, 126 125 байт

s->{int t=s.replaceAll("<","").length(),y=t-1;String r=t+++"";for(char c:s.toCharArray())r+=(c+"")+(c<61?t++:y--);return r;};

Я не думаю, що це навіть працює хе-хе

Непрограмна тестова програма

public static void main(String[] args) {
    Function<String, String> function = s -> {
        int t = s.replaceAll("<", "").length(), y = t - 1;
        String r = t++ + "";
        for (char c : s.toCharArray()) {
            r += (c + "") + (c < 61 ? t++ : y--);
        }
        return r;
    };

    System.out.println(function.apply("<<><><<"));
    System.out.println(function.apply(">>><<<"));
    System.out.println(function.apply(">>>"));
    System.out.println(function.apply("<<<"));
    System.out.println(function.apply(">><><>>"));
}

Ви можете змінити , .replaceAllщоб .replaceі видалити дужки навколо , (c+"")щоб зберегти 5 байт.
Кевін Круїйсен

@KevinCruijssen Не бідкався про 5 байт ха-ха.
Shaun Wild

При використанні належної мови для гольфу 5 байт - це різниця між 5-м та 2-м місцем. Що стосується java, це різниця між останнім місцем та останнім місцем.
Шон Уайлд

Java майже завжди буде останньою з проблемами кодового гольфу, але причина, з якої ми розміщуємо відповіді на Java, для початку - це цікаво писати її якомога коротше. Я особисто вже радий, якщо мій код Java перейде від 500 до 499 в перерахунку на байт. ; P
Кевін Круїйсен

Ми в основному ігноруємо всіх конкурентів і просто конкуруємо з або поданнями Java / C # тощо.
Shaun Wild

4

Желе , 27 14 12 байт

Порт @Martin Enders CJam розчин
-2 байти завдяки @Dennis

żJ0;µFṣ”<Uj”<

Перевірте це на TryItOnline

Як?

żJ0;Fṣ”<Uj”< - main link takes an argument, the string, e.g. ><>
 J           - range(length(input)), e.g. [1,2,3]
  0          - literal 0
   ;         - concatenate, e.g. [0,1,2,3]
ż            - zip with input, e.g. [[0],">1","<2",">3"]
    F        - flatten, list, e.g. "0>1<2>3"
      ”<  ”< - the character '<'
     ṣ       - split, e.g. ["0>1","2>3"]
        U    - upend (reverse) (implicit vectorization), e.g. ["1>0","3>2"]
         j   - join, e.g. "1>0<3>2"

Попередній метод був цікавий математично, але не настільки гофрований ...

=”>U
LR!×ÇĖP€S‘
L‘ḶŒ!ị@ÇðżF

Для цього використовується факторна базова система, щоб знайти індекс перестановок [0, N], який задовольнить рівняння.


1
Uвекторизує, тож вам не потрібно . żJ0;зберігає ще один байт.
Денніс

4

Clojure, 152 132 126 байт

(defn f[s](loop[l 0 h(count s)[c & r]s a""](if c(case c\<(recur(inc l)h r(str a l c))(recur l(dec h)r(str a h c)))(str a l))))

Збережено неабияку кількість байтів, усунувши стільки пробілів, скільки я міг. Я зрозумів, що пробіли не потрібні для відокремлення дужок від іншого символу.

В основному порт Clojure відповіді @ Scepheo. Працює однаково.

Ці recurдзвінки вбивчі! Я думаю, я міг би використовувати атоми, щоб очистити його. Theswap! виклики , необхідні для використання атомів додаються до графи: /

Завдяки @amalloy, що врятував мені кілька байт.

Безголівки:

(defn comp-chain [chain-str]
  (loop [l 0 ; Lowest number
         h (count chain-str) ; Highest number
         [c & cr] chain-str ; Deconstruct the remaining list
         a ""] ; Accumulator
    (if c ; If there's any <>'s left
      (if (= c \<) ; If current char is a <...
        (recur (inc l) h cr (str a l c)) ; Add l to a, and inc l
        (recur l (dec h) cr (str a h c))) ; Add h to a, and dec h
      (str a l)))) ; Add on the remaining lowest number, and return

Ласкаво просимо на сайт!
DJMcMayhem

@DJMcMayhem Дякую Сподіваюся, наступного разу я зможу придумати власне рішення, а не просто перенести ще одну відповідь.
Carcigenicate

Ви можете зберегти ще два пробіли у loopпалітурці до sі після a. Крім того, можна голитися трохи, замінивши ifдерево з case: (case c \< (recur ...) nil (str ...) (recur ...)). І звичайно crможе бути коротша назва.
amalloy

@amalloy Добре, дякую. Я оновлю, коли перейду на ноутбук.
Carcigenicate

3

Haskell, 162 байти

import Data.List
(a:b)%(c:d)=show c++a:b%d
_%[x]=show x
f l=map(l%).filter(l#)$permutations[0..length l]
(e:f)#(x:y:z)=(e!x)y&&f#(y:z)
_#_=0<1
'>'!x=(>)x
_!x=(<)x

Це тривалий час.


3

Perl (107 + 1 для -p) 108

for$c(split''){$s.=$i++.$c;}
for$b(split'<',$s.$i){$h[$j]=join'>',reverse split'>',$b;$j++;}
$_=join'<',@h;

Алгоритм вкрадені з Мартіна Ендер ♦ 's відповіді


2

Рубін, 135 байт

g=gets
puts g.nil?? 0:[*0..s=g.size].permutation.map{|a|a.zip(g.chars)*""if s.times.map{|i|eval"%s"*3%[a[i],g[i],a[i+1]]}.all?}.compact

Примітка: Складність часу велика (O (n!)).


2

Python 2, 176 172 байт

Це не дуже коротко в порівнянні з іншими, але я щасливий, що вирішив це так швидко.

from itertools import*
def f(s):
 for p in permutations(range(len(s)+1)):
    n=list(s);p=list(p);t=[p.pop()]+list(chain(*zip(n,p)));r="".join(map(str,t))
    if eval(r):return r

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

Безголівки:

from itertools import*
def f(s):
    n=list(s);R=range(len(s)+1)
    for p in permutations(R):
        p=list(p)
        r=[p.pop()]
        t=n+p
        t[::2]=n
        t[1::2]=p
        r="".join(map(str,r+t))
        if eval(r):return r

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


частина переплетення може бути набагато коротшеzip
Мальтісен

@Maltysen Не на тон коротший, бо списки не однакової довжини (я все одно повинен pop), але трохи коротший. Якби N<10, я міг би зробити стрифікацію коротшою.
mbomb007

1

PHP, 190 байт

випадкове переміщення, поки не існує дійсного рішення

$x=range(0,$l=strlen($q=$argv[1]));while(!$b){$b=1;$t="";shuffle($x);for($i=0;$i<$l;){$t.=$x[$i].$q[$i];if(($q[$i]==">"&$x[$i]<$x[$i+1])|($q[$i]=="<"&$x[$i]>$x[1+$i++]))$b=0;}}echo$t.$x[$i];

381 байт отримати всі рішення та вибрати один

<?php $d=range(0,strlen($q=$argv[1]));echo $q."\n";$e=[];function f($t=""){global$e,$d,$q;foreach($d as$z){preg_match_all("#\d+#",$t,$y);if(in_array($z,$y[0]))continue;$p=preg_match_all("#[<>]#",$t);$g="";if(preg_match("#\d+$#",$t,$x)){if(($q[$p]==">"&$x[0]<$z)|($q[$p]=="<"&$x[0]>$z))continue;$g=$q[$p];}strlen($q)==$p+1|!$q?$e[]=$t.$g.$z:f($t.$g.$z);}}f();echo$e[array_rand($e)];
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.