На скільки штук можна вирізати цю струну?


45

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

Візьмемо як приклад [-1, 3, 1, -2, 5, 2, 3, 4](зауважте, що не кожен запис має на увазі складку):

введіть тут опис зображення

Рядок, що проходить уздовж вертикального напрямку, призначений лише для візуалізації. Уявіть, що струна все сплющена на реальній лінії.

Тепер ось питання: якою є найбільша кількість штук, яку можна нарізати цією струною одним вирізом (який повинен бути вертикальним на малюнку вище). У цьому випадку відповідь - 6 із вирізом у будь-якому місці між 2та 3:

введіть тут опис зображення

Щоб уникнути неоднозначності, розріз повинен бути виконаний в нецілих положенні.

Змагання

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

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

Ви можете припустити, що список знаходиться у будь-якому зручному списку чи рядковому форматі.

Список міститиме щонайменше 2 та не більше 100 записів. Записи будуть цілими числами, кожне в діапазоні -2 31 ≤ p i <2 31 . Можна припустити, що жодна дві послідовні записи не однакові.

Ваш код повинен обробити будь-який такий вхід (включаючи тестові приклади нижче) протягом менш ніж 10 секунд на розумному настільному ПК.

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

Усі тестові приклади просто вводяться з подальшим результатом.

[0, 1]
2

[2147483647, -2147483648]
2

[0, 1, -1]
3

[1, 0, -1]
2

[-1, 3, 1, -2, 5, 2, 3, 4]
6

[-1122432493, -1297520062, 1893305528, 1165360246, -1888929223, 385040723, -80352673, 1372936505, 2115121074, -1856246962, 1501350808, -183583125, 2134014610, 720827868,  -1915801069, -829434432, 444418495, -207928085, -764106377, -180766255, 429579526,  -1887092002, -1139248992, -1967220622, -541417291, -1617463896, 517511661, -1781260846,  -804604982, 834431625, 1800360467, 603678316, 557395424, -763031007, -1336769888,  -1871888929, 1594598244, 1789292665, 962604079, -1185224024, 199953143, -1078097556, 1286821852, -1441858782, -1050367058, 956106641, -1792710927, -417329507, 1298074488,  -2081642949, -1142130252, 2069006433, -889029611, 2083629927, 1621142867, -1340561463,  676558478, 78265900, -1317128172, 1763225513, 1783160195, 483383997, -1548533202,  2122113423, -1197641704, 319428736, -116274800, -888049925, -798148170, 1768740405,  473572890, -1931167061, -298056529, 1602950715, -412370479, -2044658831, -1165885212,  -865307089, -969908936, 203868919, 278855174, -729662598, -1950547957, 679003141,  1423171080, 1870799802, 1978532600, 107162612, -1482878754, -1512232885, 1595639326,  1848766908, -321446009, -1491438272, 1619109855, 351277170, 1034981600, 421097157,  1072577364, -538901064]
53

[-2142140080, -2066313811, -2015945568, -2013211927, -1988504811, -1884073403, -1860777718,  -1852780618, -1829202121, -1754543670, -1589422902, -1557970039, -1507704627, -1410033893,  -1313864752, -1191655050, -1183729403, -1155076106, -1150685547, -1148162179, -1143013543,  -1012615847, -914543424, -898063429, -831941836, -808337369, -807593292, -775755312, -682786953, -679343381, -657346098, -616936747, -545017823, -522339238, -501194053,  -473081322, -376141541, -350526016, -344380659, -341195356, -303406389, -285611307, -282860017, -156809093, -127312384, -24161190, -420036, 50190256, 74000721, 84358785,  102958758, 124538981, 131053395, 280688418, 281444103, 303002802, 309255004, 360083648,  400920491, 429956579, 478710051, 500159683, 518335017, 559645553, 560041153, 638459051,  640161676, 643850364, 671996492, 733068514, 743285502, 1027514169, 1142193844, 1145750868,  1187862077, 1219366484, 1347996225, 1357239296, 1384342636, 1387532909, 1408330157,  1490584236, 1496234950, 1515355210, 1567464831, 1790076258, 1829519996, 1889752281,  1903484827, 1904323014, 1912488777, 1939200260, 2061174784, 2074677533, 2080731335, 2111876929, 2115658011, 2118089950, 2127342676, 2145430585]
2

Можемо припустити, що ви хочете, щоб розріз був у місці, яке гарантує максимальну кількість штук?
DavidC

2
Я б, напевно, сказав: "визначте найбільшу кількість штук", а не "визначте, скільки штук".
DavidC

1
Це не a reasonable desktop PCдосить неоднозначно?
глобі

3
@globby Це досить поширена фраза, яку ми використовуємо, коли час виконання не є частиною критерію виграшу (але використовується лише для того, щоб рішення не використовували грубу силу). Це здебільшого означає, що межа не є 100% суворим. Якщо на вашій машині потрібно 15 секунд (а ви не використовуєте суперкомп'ютер), швидше за все, хтось тут має настільний ПК, де він завершиться за 10 секунд. Але якщо на вашій машині потрібна хвилина, це менш ймовірно, тож вам доведеться подумати про інший підхід. Крім того, ліміт вибирається таким, що ефективний алгоритм легко завершиться за 10 секунд.
Мартін Ендер

Відповіді:


16

APL, 16 14 байт

1+⌈/+/2≠/∘.≤⍨⎕

Завдяки @ngn за збереження 2 байтів.

Насправді коробка характер, а не помилка відсутнього шрифту. Ви можете спробувати програму на tryapl.org , але оскільки вона не повністю підтримується, вам доведеться замінити її на вхідне значення:

    1+⌈/+/2≠/∘.≤⍨ ¯1 3 1 ¯2 5 2 3 4
6

Пояснення

Програма найкраще пояснюється на прикладі введення s = ¯1 3 1 ¯2 5 2 3 4, який береться у STDIN . По-перше, ми обчислюємо продукт -outer sіз самим собою, використовуючи ∘.≤⍨. Це призводить до отримання булевої матриці, чий iрядок вказує, для яких елементів sменше або дорівнює s[i]:

1 1 1 0 1 1 1 1
0 1 0 0 1 0 1 1
0 1 1 0 1 1 1 1
1 1 1 1 1 1 1 1
0 0 0 0 1 0 0 0
0 1 0 0 1 1 1 1
0 1 0 0 1 0 1 1
0 0 0 0 1 0 0 1

Події 0 1та 1 0на рядок iпозначають місця, де рядок проходить над точкою s[i] + 0.5. Ми порівнюємо їх у кожному рядку, використовуючи 2≠/"зменшити 2-х списків ":

0 0 1 1 0 0 0
1 1 0 1 1 1 0
1 0 1 1 0 0 0
0 0 0 0 0 0 0
0 0 0 1 1 0 0
1 1 0 1 0 0 0
1 1 0 1 1 1 0
0 0 0 1 1 0 1

Залишилося взяти суми рядків +/

2 5 3 0 2 3 5 3

і один плюс максимум з них 1+⌈/:

6

Результат автоматично надрукується в STDOUT у більшості реалізацій APL.


@ n̴̖̋h̷͉̃a̷̭̿h̸̡̅ẗ̵̨́d̷̰̀ĥ̷̳ Мій поганий очікуваний результат - кількість штук, а не місце для їх виготовлення.
J ...

Технічно це 16 символів, 28 байт. Unicode зробить це вам = P
KChaloux

1
@KChaloux, лише якщо ви порахуєте у utf8 байтах, чого ви б не APL. Існує однобайтова кодова сторінка, яка містить весь набір символів, використовуваний APL, тому справедливо використовувати це для підрахунку.
Мартін Ендер

@ MartinBüttner Надійне посилання на джерело було б чудово. В іншому випадку, хтось може створити довільну веб-сторінку із власним набором символів для будь-якої мови, щоб зменшити кількість байтів.
agweber

1
@GuillaumeLethuillier APL насправді навчитися дуже просто, принаймні, до того моменту, коли можна написати прості відповіді на гольф, як це. Є кілька десятків функцій з легкими для запам'ятовування іменами, як ×для множення, і дуже простими правилами синтаксису. Google "освоює Dyalog APL" для хорошого керівництва.
Згарб

16

Пітон, 88 75 73 байт

lambda x:max(sum((a+.5-m)*(a+.5-n)<0for m,n in zip(x,x[1:]))for a in x)+1

Просто прямолінійна лямбда


Просто щоб показати інший підхід:

Pyth, 28 27 байт

heSmsmq@S+k(d)1dC,QtQm+b.5Q

Це приблизно рівнозначно

lambda x:max(sum(a+.5==sorted(n+(a+.5,))[1]for n in zip(x,x[1:]))for a in x)+1

застосовано до списку введення від STDIN. Спробуйте це на онлайн-перекладачі .


Ви навіть можете зберігати цю функцію в тій же кількості символів:def f(x):max(sum((a+.5-m)*(a+.5-n)<0for m,n in zip(x,x[1:]))for a in x)+1
Крістіан Сонне,

4
@ChristianSonne Ваша функція нічого не повертає.
Якубе

Стріляйте, ви маєте рацію @Jakube
Крістіан Сонне

Я не зовсім впевнений, як це працює, але я думаю, що ви можете видалити +.5s, щоб зберегти деякі символи. Я зрозумів, що вони безглузді в моєму.
KSFT

@KSFT Він розбиває рядок на інтервали, повторює кожен a = point + .5і підраховує кількість строго містять інтервалів a. Без у .5вас виникнуть проблеми у випадках, як на [1, 0, -1]прикладі.
Sp3000

16

Pyth : 31 30 29 28 24 23 персонаж (Python 68 chars)

heSmsm&<hSkdgeSkdC,tQQQ

Спробуйте тут: компілятор / виконавець Pyth

Він очікує список цілих чисел як вхід [-1, 3, 1, -2, 5, 2, 3, 4]

Це прямий переклад моєї програми Python:

lambda s:1+max(sum(min(a)<i<=max(a)for a in zip(s,s[1:]))for i in s)

Старе рішення: Pyth 28 char

Просто з архівних причин.

heSmsm<*-dhk-dek0C,tQQm+b.5Q

Відповідним кодом Python буде:

f=lambda x:1+max(sum((i-a)*(i-b)<0for a,b in zip(x,x[1:]))for i in [j+.5 for j in x])

Досить впевнений, що ви можете використовувати ,QtQзамість[QtQ)
FryAmTheEggman

iне лінія перетину, i - 0.5є. І тому 1 (власне 1 - 0.5 = 0.5) знаходиться всередині (-1, 1). min(a)<i<=max(a)еквівалентний тому min(a) < i - 0.5 < max(a), що вирішується в Pyth з min(a) < i < max(a)+1(зверніть увагу на hв heSk).
Якубе

Я думаю, ти тут. Або принаймні я не можу знайти жодного випадку, коли ця логіка виходить з ладу ...
Оптимізатор

Ви можете зберегти символ, використовуючи g, що є >=, якщо ви заміните <dheSkна geSkd.
isaacg

2
Дякую @isaacg Але чому ти завжди йдеш і руйнуєш моє рішення, коли я справді щасливий і впевнений у цьому? ;-)
Якубе

10

CJam, 36 34 33 30 байт

q~[__(+]zW<f{f{1$+$#1=}1b}$W=)

Я вважаю, що в дикій природі існує кращий алгоритм. Однак це працює в межах, необхідних для всіх тестових випадків (навіть для онлайн-компілятора)

Введення подібне

[-2142140080 -2066313811 -2015945568 -2013211927 -1988504811 -1884073403 -1860777718  -1852780618 -1829202121 -1754543670 -1589422902 -1557970039 -1507704627 -1410033893  -1313864752 -1191655050 -1183729403 -1155076106 -1150685547 -1148162179 -1143013543  -1012615847 -914543424 -898063429 -831941836 -808337369 -807593292 -775755312 -682786953 -679343381 -657346098 -616936747 -545017823 -522339238 -501194053  -473081322 -376141541 -350526016 -344380659 -341195356 -303406389 -285611307 -282860017 -156809093 -127312384 -24161190 -420036 50190256 74000721 84358785  102958758 124538981 131053395 280688418 281444103 303002802 309255004 360083648  400920491 429956579 478710051 500159683 518335017 559645553 560041153 638459051  640161676 643850364 671996492 733068514 743285502 1027514169 1142193844 1145750868  1187862077 1219366484 1347996225 1357239296 1384342636 1387532909 1408330157  1490584236 1496234950 1515355210 1567464831 1790076258 1829519996 1889752281  1903484827 1904323014 1912488777 1939200260 2061174784 2074677533 2080731335 2111876929 2115658011 2118089950 2127342676 2145430585]

Вихід (для вищевказаного випадку) є

2

Як це працює

q~[__(+]zW<f{f{1$+$#1=}1b}$W=)
q~                                "Evaluate input string as array";
  [__                             "Put two copies of it in an array";
     (+]                          "Shift first element of second copy to its end";
        z                         "Zip together the two arrays. This creates";
                                  "pair of adjacent elements of the input.";
         W<                       "Remove the last pair";
           f{            }        "For each element of input array, take the zipped";
                                  "array and run the code block";
             f{       }           "For each element of the zipped array along with";
                                  "the current element from input array, run this block";
               1$+                "Copy the current number and add it to the pair";
                  $#              "Sort the pair and find index of current number";;
                    1=            "check if index == 1 for a < I <= b check";
                       1b         "Get how many pairs have this number inside of them";
                          $W=)    "Get the maximum parts the rope can be cut into";

Тепер припустимо, що вхідний масив є [-1 3 1 -2 5 2 3 4], кроки блискавки виглядають так:

[-1 3 1 -2 5 2 3 4] [[-1 3 1 -2 5 2 3 4] [-1 3 1 -2 5 2 3 4]
[-1 3 1 -2 5 2 3 4] [[-1 3 1 -2 5 2 3 4] [3 1 -2 5 2 3 4 -1]
[-1 3 1 -2 5 2 3 4] [[-1 3] [3 1] [1 -2] [-2 5] [5 2] [2 3] [3 4]]]

Другий масив в останньому рядку - це складки рядка.

Тепер ми повторюємо [-1 3 1 -2 5 2 3 4]і обчислюємо кількість наборів, в яких кожен з них лежить. Отримайте максимум від цього числа, збільште його, і ми отримаємо свою відповідь.

Спробуйте його онлайн тут


10

Матлаб (123) (97) (85)

Так, нарешті, використання для XNOR =) Я впевнений, що це може бути набагато більше.

Але, чесно кажучи, я трохи збентежений, що MatLab стає мовою, яку я найкраще знаю = /

Орієнтовний час виконання O(n^2).

EDIT2:

a=input();v=2:nnz(a);disp(max(arrayfun(@(e)sum(~xor(a(v-1)<e,e<a(v))),sort(a)-.5))+1)

EDIT: Нова версія для гольфу (включаючи підказки від @DennisJaheruddin, дякую!)

a=input();c=sort(a)-.5;n=0;v=2:nnz(c);for e=c;n=[n,sum(~xor(a(v-1)<e,e<a(v)))];end;disp(max(n)+1)

Стара версія:

a=input();
c=conv(sort(a),[.5,.5],'valid');' %find all cutting positions by taking the mean of two successive points
k=numel(c);
for e=1:k %iterate over all 'cuts'
    n(e)=sum(~xor(a(1:k)<c(e),c(e)<a(2:k+1)));%find the number of threads the cut cuts
end
disp(max(n)+1) %output the max

@ MartinBüttner: Я дуже насолоджуюся твоїм прекрасним маленьким викликом, що лежить перед сном!


10
Моя дружина не витримує XNORing
гніблер

9
Час для @xnor робити нотатки =)
помилка

Я думаю, що ви можете заощадити в пошуку точок різання, оскільки складки завжди цілі: c=sort(a)-.5Звичайно, перша точка - це поза межами діапазону, але, безумовно, з цим легше впоратися. У гіршому випадку ви можете це зробити c(1)=[];. - Також ви можете зняти команду disp, просто обчисливши щось, буде numelnnz
записано

Але я так пишався своїм convпідходом ... = D. Я завжди забуваю про те nnz, дуже дякую!
flawr

Я міг знайти досить багато способів зробити це ще коротше! Я використовую, dispоскільки хтось колись критикував, що за запропонованим вами методом ви також отримуєте інші символи (ім'я ans
вару

9

Mathematica 134 133 104

Весело вирішувати, незважаючи на розмір коду. Далі гра в гольф все ще може бути досягнуто шляхом заміни ідеї IntervalMemberQ[Interval[a,b],n]з a<n<b.

n_~f~i_:=Count[IntervalMemberQ[#,n]&/@i,1>0];
g@l_:=Max[f[#,Interval/@Partition[l,2,1]]&/@(Union@l+.5)]+1

g[{-1, 3, 1, -2, 5, 2, 3, 4}]

6


Пояснення

list1це наведений список точок list2- скорочений список, який видаляє числа, які не були в складках; вони не мають значення. Цього робити не обов’язково, але це призводить до більш чіткого та ефективного рішення.

list1 = {-1, 3, 1, -2, 5, 2, 3, 4};
list2 = {-1, 3, 1, -2, 5,2, 3, 4} //. {beg___, a_, b_, c_, end___} /; (a <= b <= c) 
 \[Or] (a >= b >= c) :> {beg, a, c, end}

Інтервали в list1і list2показані на графіках нижче:

NumberLinePlot[Interval /@ Partition[list1, 2, 1]]
NumberLinePlot[intervalsArrangedVertically = Interval /@ Partition[list2, 2, 1]]

інтервали


Нам потрібно лише протестувати по одному рядку на кожному інтервалі, визначеному точками згину. Тестові лінії - пунктирні вертикальні лінії на графіку.

delimitersLeftToRight = Union[list2]
testLines = delimitersLeftToRight + .5
NumberLinePlot[
 intervalsArrangedVertically = Interval /@ Partition[list2, 2, 1], 
 GridLines -> {testLines, {}}, 
 GridLinesStyle -> Directive[Gray, Dashed]]

тестові лінії


fзнаходить кількість розрізів або перетинів кожного тестового рядка. Лінія при х = 2,5 робить 5 перетинів. При цьому залишається 5 + 1 шматок струни.

f[num_, ints_] := Count[IntervalMemberQ[#, num] & /@ ints, True]
f[#, intervalsArrangedVertically] & /@ testLines
Max[%] + 1

{2, 3, 5, 3, 2, 0}
6


8

Pyth, 21 байт

heSmsmq1xS+dSkdC,tQQQ

Спробуйте тут.

Введіть дані як список стилів Python, наприклад [-1, 3, 1, -2, 5, 2, 3, 4]

Тісно засноване на програмі @ jakube, але з покращеним центральним алгоритмом. Замість того, щоб робити >перевірку та >=перевірку, я роблю атрибути .index()на трьох числах і переконуюсь, що індекс дорівнює 1, це означає, що він більший за мінімальний і менший або рівний максимальному.


7

R, 86 83

Я працював над цим, а потім зрозумів, що я по суті придумав таке ж рішення, як і Оптимізатор та інші, які я підозрюю.

У будь-якому випадку це функція, яка приймає вектор

f=function(l)max(colSums(mapply(function(n)c(l[-1],NA,l)<=n&c(l,l[-1],NA)>=n,l),T))

Гаразд, тому я упереджений і просто люблю R. FWIW ви можете зберегти 3 символи, скориставшись T"TRUE"
Carl Witthoft

@CarlWitthoft Дякую за підказку
MickyT

4

GolfScript (43 байти)

~[.(;]zip);{$}%:x{0=:y;x{{y>}%2,=},,}%$-1=)

З точки зору ефективності це O (n ^ 2), припускаючи, що порівняння займають O (1) час. Він розбиває вхід на відрізки рядків і для кожної початкової точки підраховує напіввідкриті відрізки рядків, які перетинають його.

Демонстрація в Інтернеті


4

Пітон - 161

Це, ймовірно, може бути більше гольфу. gnibbler дуже допомагав цьому в гольфі.

l=input()
d={}
for i in zip(l,l[1:]):d[sum(i)/2.]=0
for i,k in zip(l,l[1:]):
 for j in[m for m in d.keys()if min(i,k)<m<max(i,k)]:d[j]+=1
print max(d.values())+1

1
@ MartinBüttner / Jakube Я це виправив. Тепер він працює для всіх тестових випадків за десять секунд.
KSFT

Чому на цьому є дві анкети?
KSFT

3

Рубі, 63

Подібно до рішень Python в концепції.

->a{a.map{|x|a.each_cons(2).count{|v|v.min<x&&x<=v.max}}.max+1}

Додайте 2 символи перед кодом, наприклад, f=якщо ви хочете назвати функцію. Thx для MarkReed .


Голий пророк видається прийнятною відповіддю, не привласнюючи його змінної. Зберігає два символи.
Марк Рід

3

C #, 73 65 байт

N=>1+N.Max(i=>N.Zip(N.Skip(1),(f,s)=>f<i+.5==i+.5<s).Count(b=>b))

Читаючи правила, я подумав, що C # лямбда має робити досить добре.

Редагувати: щойно знайдене Countкорисне перевантаження для фільтрації!

Ви можете перевірити це, визначивши відповідний delegateтип:

delegate int solver(int[] l);

І потім

var l = new int[] { -1, 3, 1, -2, 5, 2, 3, 4 };
solver s = N=>1+N.Max(i=>N.Zip(N.Skip(1),(f,s)=>f<i+.5==i+.5<s).Count(b=>b));

Console.WriteLine(s(l));

3

Матлаб ( 63 43)

Введення задається як вектор рядка, переданий функції f. Так, наприклад, f([-1, 3, 1, -2, 5, 2, 3, 4])повертається 6.

f=@(x)max(sum(diff(bsxfun(@le,2*x',x(1:end-1)+x(2:end)))~=0))+1

Коротша версія:

f=@(x)max(sum(diff(bsxfun(@lt,x',x))~=0))+1

Октава (31)

У Octave bsxfunможна видалити завдяки автоматичному мовленню:

f=@(x)max(sum(diff(x'<x)~=0))+1

2

JavaScript (ES6) 80 82

Дивіться коментарі - кількість байтів не включає призначення F (це все ще потрібно для тестування)

F=l=>Math.max(...l.map(v=>l.map(t=>(n+=t>u?v<t&v>=u:v>=t&v<u,u=t),n=1,u=l[0])&&n))

Тест в консолі FireFox / FireBug

;[
 F([0, 1])
,F([2147483647, -2147483648])
,F([0, 1, -1])
,F([1, 0, -1])
,F([-1, 3, 1, -2, 5, 2, 3, 4])  
,F([-1122432493, -1297520062, 1893305528, 1165360246, -1888929223, 385040723, -80352673, 1372936505, 2115121074, -1856246962, 1501350808, -183583125, 2134014610, 720827868, -1915801069, -829434432, 444418495, -207928085, -764106377, -180766255, 429579526, -1887092002, -1139248992, -1967220622, -541417291, -1617463896, 517511661, -1781260846, -804604982, 834431625, 1800360467, 603678316, 557395424, -763031007, -1336769888, -1871888929, 1594598244, 1789292665, 962604079, -1185224024, 199953143, -1078097556, 1286821852, -1441858782, -1050367058, 956106641, -1792710927, -417329507, 1298074488, -2081642949, -1142130252, 2069006433, -889029611, 2083629927, 1621142867, -1340561463, 676558478, 78265900, -1317128172, 1763225513, 1783160195, 483383997, -1548533202, 2122113423, -1197641704, 319428736, -116274800, -888049925, -798148170, 1768740405,  473572890, -1931167061, -298056529, 1602950715, -412370479, -2044658831, -1165885212, -865307089, -969908936, 203868919, 278855174, -729662598, -1950547957, 679003141,  1423171080, 1870799802, 1978532600, 107162612, -1482878754, -1512232885, 1595639326, 1848766908, -321446009, -1491438272, 1619109855, 351277170, 1034981600, 421097157, 1072577364, -538901064])
,F([-2142140080, -2066313811, -2015945568, -2013211927, -1988504811, -1884073403, -1860777718, -1852780618, -1829202121, -1754543670, -1589422902, -1557970039, -1507704627, -1410033893,  -1313864752, -1191655050, -1183729403, -1155076106, -1150685547, -1148162179, -1143013543,  -1012615847, -914543424, -898063429, -831941836, -808337369, -807593292, -775755312, -682786953, -679343381, -657346098, -616936747, -545017823, -522339238, -501194053,  -473081322, -376141541, -350526016, -344380659, -341195356, -303406389, -285611307, -282860017, -156809093, -127312384, -24161190, -420036, 50190256, 74000721, 84358785,  102958758, 124538981, 131053395, 280688418, 281444103, 303002802, 309255004, 360083648,  400920491, 429956579, 478710051, 500159683, 518335017, 559645553, 560041153, 638459051,  640161676, 643850364, 671996492, 733068514, 743285502, 1027514169, 1142193844, 1145750868,  1187862077, 1219366484, 1347996225, 1357239296, 1384342636, 1387532909, 1408330157,  1490584236, 1496234950, 1515355210, 1567464831, 1790076258, 1829519996, 1889752281,  1903484827, 1904323014, 1912488777, 1939200260, 2061174784, 2074677533, 2080731335, 2111876929, 2115658011, 2118089950, 2127342676, 2145430585])
]

Вихід

[2, 2, 3, 2, 6, 53, 2]


2
На основі lambdaрішень Python вам не потрібно присвоювати значення функції фактичній змінній, тому ви можете зняти два символи.
Марк Рід

1
Так. Якщо у виклику не вказано інше, неназвані функції ідеально чудові.
Мартін Ендер




0

Додайте ++ , 27 байт

D,w,@@,VbUG€<ÑBxs
L~,A€wM1+

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

Підходьте дякую Згарбу за відповідь APL

Ключова частина цього завдання - реалізація зовнішньої команди продукту. На жаль, Add ++ не має вбудованого для цього, не має жодного способу визначення функцій, які приймають інші функції як аргументи. Однак ми все-таки можемо зробити узагальнену функцію зовнішнього продукту. Оскільки єдиним способом доступу до функції в іншій функції є посилання на існуючу функцію, визначену користувачем або вбудовану функцію, ми повинні створити "вбудований", який посилається на таку функцію.

Узагальнена функція "таблиця" виглядатиме приблизно так:

D,func,@@,+

D,iter,@@*, VbUG €{func}
D,table,@@, $ bRbU @ €{iter} B]

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

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

Загальна функція таблиці використовує переваги швидкого наближення діадічних функцій. Якщо стек виглядає так

 [a b c d e]

коли €{func}стикається, pops e, прив'язує це як лівий аргумент до діади, і відображає цю часткову функцію a, b, c, d. Однак швидкі карти на весь стек, а не на списки. Тому нам потрібно спочатку розрівняти передані масиви як аргументи.

Функція таблиці працює в цілому так

D,func,@@,+

D,iter,		; Define our helper function iter
		;   This takes an array as its left argument
		;   And a single integer as its right argument
	@@	; Dyadic arguments - take two arguments and push to the stack
	*,	; After execution, return the entire stack, rather then just the top element
		;
		; Example arguments:	[5 6 7 8] 1
		; 
	VbUG	; Unpack the array;	[5 6 7 8 1]
		;
	€{func}	; Map func over the stack
		; As func is dyadic, this pops the right argument
		;   and binds that to a monadic func
		; This then maps the remaining elements, [5 6 7 8]
		;   over the monadic call of func, yielding [6 7 8 9]
		; Now, as the * flag was defined, we return the entire array
		;   rather than just the last element.
		; We'd achieve the same behaviour by removing the flag and appending B]

D,table,	; Define the main table function
		;   This takes two arrays as arguments
		;   Returns a single 2D array representing their outer product with func
	@@,	; Take the two arrays and push to the stack
		; 
		; Example arguments:	[[1 2 3 4] [5 6 7 8]]
		;
	$	; Swap;		STACK = [[5 6 7 8] [1 2 3 4]]
	bR	; Reverse last;	STACK = [[5 6 7 8] [4 3 2 1]]
	bU	; Unpack;	STACK = [[5 6 7 8] 4 3 2 1]
	@	; Reverse;	STACK = [1 2 3 4 [5 6 7 8]]
		; 
		; This allows us to place the stack so that each element of
		;   the first array is iterated over with the second array
		;
	€{iter}	; Map iter;	STACK = [[6 7 8 9] [7 8 9 10] [8 9 10 11] [9 10 11 12]]
		;
	B]	; Return the whole stack;

$table>?>?
O

Однак ми можемо скоротити це досить багато через те, що нам потрібна наша зовнішня таблиця, щоб бути монадичною , і потрібно лише звернутися до переданого аргументу. AКоманда поміщає кожен аргумент в стек по окремо, так що нам не потрібно возитися з будь-маніпуляцією стеки. Якщо коротко, якщо наш аргумент - це масив [a b c d], нам потрібно зробити стек

[a b c d [a b c d]]

Верхнє значення, звичайно, argument.You , можливо, зауважив із загального прикладу , що bUє розпакуванням команди тобто Splats верхнього масиву в стеку. Отже, щоб зробити описану вище конфігурацію, ми можемо використовувати код

L,bUA

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

Однак це можна скоротити на байт. Як псевдонім для L,bU, ми можемо використовувати ~прапор, щоб заздалегідь викласти аргументи в стек, зробивши наш приклад конфігурації в

L~,A

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

що є початком другого рядка програми. Тепер ми реалізували монадічний зовнішній продукт, нам просто потрібно реалізувати решту алгоритму. Отримавши результат таблиці з <(менше, ніж), і підрахуйте кількість [0 1]та [1 0]пари в кожному рядку. Нарешті, ми беремо максимум цих підрахунків і збільшуємо його.

Повний крок для крокової прогулянки - це

D,w,		; Define a function w
		;   This takes an array and an integer as arguments
		;   First, it produces the outer product with less than
		;   Then reduce overlapping pairs by XOR
		;   Finally, sum the rows
	@@,	; Take two arguments
		;
		; Example arguments:		[[0 1 2 3] 0]
		;
	VbUG€<	; Map < over the array;	STACK = [0 1 1 1]
	ÑBx	; Equals [1 0];		STACK = [1 0 0]
	s	; Sum;			STACK = [1]

L		; Define a lambda function
		;   This takes one argument, an array
	~,	;   Splat the array to the stack before doing anything
		;
		; Example argument:		[0 1 2 3]
		;
	A€w	; Map with w;		STACK = [1 1 1 0]
	M	; Maximum;		STACK = [1]
	1+	; Increment;		STACK = [2]
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.