Мини-гольф по понедельникам: серия коротких соревнований по коду , публикуемых (надеюсь!) Каждый понедельник.
Последовательность, подобная Фибоначчи, получается с использованием того же метода, что и известная последовательность Фибоначчи ; то есть каждое число F (n) находится путем сложения двух предыдущих чисел в последовательности ( F (n) = F (n-1) + F (n-2) ) или путем вычитания следующих двух чисел ( F (n) = F (n + 2) - F (n + 1) ). Основное отличие состоит в том, что эти последовательности могут начинаться с любых двух чисел. Обнуление этих последовательностей является спорным, но сейчас мы собираемся использовать это правило:
- 0-е число в последовательности, подобной Фибоначчи, является последним числом, которое меньше предыдущего числа.
В качестве примера, последовательность Фибоначчи может быть записана как 1, 0, 1, 1, 2, 3, 5...
, поэтому 0-е число в последовательности является единственным 0
.
Вызов
Цель задачи - написать программу или функцию, которая принимает три целых числа в любом формате:
- A и B , два числа, с которых начинается генерация последовательности.
- N - длина полученной последовательности для вывода.
И выводит первые N чисел последовательности, начиная с 0-го.
Детали
- A , B и N могут быть взяты в любом порядке и формате, если они визуально разделены. Если вы используете другой порядок / формат, пожалуйста, укажите, что это такое.
- Вы можете предположить, что A , B и N всегда являются положительными целыми числами.
- Можно предположить, что N не более 100, и результирующая последовательность не будет содержать
x >= 2^31
. - Если A больше, чем B , то B - это 0-е число в последовательности.
- Вывод должен быть разделен пробелами, запятыми и / или символами новой строки.
- Допускается завершающий пробел или символ новой строки, но не запятая.
Тест-кейсы
Пример 1:
8 13 10
Работая задом наперед, 8 13
пока мы не найдем число больше предыдущего, мы получим 13 8 5 3 2 1 1 0 1
. Таким образом, 0
это 0-е число в этой последовательности. Работая над этим, мы распечатываем 0
и следующие 9 участников:
0 1 1 2 3 5 8 13 21 34
Пример 2:
23 37 5
Снова работая в обратном направлении, чтобы найти 0-е число, мы находим 37 23 14 9 5 4 1 3
. На этот раз 0-е число 1
, поэтому мы распечатываем его вместе со следующими 4 членами:
1 4 5 9 14
Пример 3:
4 3 8
С этим нам не нужно работать в обратном направлении, чтобы найти 0-е число, потому что 3
оно меньше, чем 4
:
3 7 10 17 27 44 71 115
Пример 4:
29 47 11
Результат:
1 3 4 7 11 18 29 47 76 123 199
счет
Это код-гольф , поэтому выигрывает самый короткий действительный код в байтах. Tiebreaker переходит к ранее опубликованному представлению. Победитель будет выбран в следующий понедельник, 28 сентября. Удачи!
Изменить: Поздравляю вашего победителя, @Jakube, используя Pyth за удивительные 23 байта!
[8, 13, 10]
)?Ответы:
Pyth, 23 байта
Попробуйте онлайн: демонстрация или тестовый набор
Довольно необычный стиль программирования Pyth. Иногда функциональное программирование имеет свои недостатки.
Объяснение:
источник
Сетчатка ,
6554 байтаВот,
<empty>
представляет пустую завершающую строку. Запустите код как отдельный файл с-s
флагом.Формат ввода
где числа представлены в одинарных . Вывод списка через запятую, также в унарном виде. Например:
было бы
и дать
объяснение
Сначала сокращаем
A
иB
до 0-го и -1-го элемента.+
Говорит Retina , чтобы повторять это регулярное выражение замены до тех пор , либо регулярное выражение не прекращает согласование или замена не изменяет строку. Регулярное выражениеA
попадает в группу 1 с(1*)
, а затем проверяет, чтоB
оно, по крайней мере , такое же большое, как иA
при захватеB-A
с\1(1*)
группой 2. Это гарантирует, что этот цикл завершится один разA>B
.Замена просто превращается
A,B
вB-A,A
установку соответствия$2,$1
.Теперь у нас уже есть первый номер требуемого вывода в строке (а также номер перед ним, от которого мы должны избавиться позже). Эта замена теперь добавляет еще одно число в качестве суммы последних двух чисел при получении
1
отN
. Поскольку у нас уже есть один номер, мы хотим, чтобы это произошло толькоN-1
. Мы делаем это, гарантируя,\B
что по крайней мере;11
в конце строки есть. Если мы назовем последние два значения последовательностиC
иD
, то регулярное выражение захватитC
группу 1 и,D
группу два. Мы пишем их обратно с$1$2
. Затем мы также пишем,$2$1
что переводится как,D+C
. Обратите внимание, что мы не записываем сингл, в котором1
мы соответствовалиN
тем самым уменьшая его.Наконец, мы должны избавиться от -1st элемента последовательности, а оставшаяся
;1
отN
, которую мы просто путем сопоставления либо из тех , и заменить его с пустой строкой.источник
Python 2,
9387676160 байтПолучает входные данные (в виде буквенного списка питонов
[8,10,13]
)Вырабатывает 0 семестр
Затем распечатывает последовательность дополнений, пока длина не будет достигнута
источник
for _ in[1]*l:
это сделать немного корочеexec"stuff;"*l
for _ in[1]*l:stuff
сexec"stuff;"*l
. @xnor не вставил часть материала в цикл for. Илиfor _ in[1]*l:
доexec";"*l
j>=i
наj/i
. Просто выяснил это! (Поскольку вы можете предполагать, что A, B и N всегда являются положительными целыми числами )CJam,
2623 байтаСпасибо Деннису за сохранение 3 байта.
Принимает ввод по порядку
N B A
(разделенный пробелами любого вида). Печатает результат как разделенный новой строкой список и завершается с ошибкой .Проверьте это здесь.
объяснение
Это идет на шаг дальше при поиске 0-го элемента. То есть он завершается, когда одно из значений является отрицательным.
источник
q~{_@\-_g)}g\@{_@+_p}*t
(N B A
) сохраняет три байта.B>A
это, нужно проверятьB not smaller than A
или что-то еще, но я не могу понять, как это сделать в CJam. РЕДАКТИРОВАТЬ: решение Денниса печатает правильный вывод.<!
вместо>
.!
в это. Я просто добавил один, чтобы он работал;)Лабиринт ,
5854494644 байтаСпасибо Sp3000 за предложение использовать побитовое отрицание, которое сэкономило два байта.
Формат ввода есть
B A N
. Выводом является разделенный новой строкой список.объяснение
(Немного устарела. Основная идея все та же, но схема кода теперь другая.)
Это использует ту же идею, что и мой ответ CJam (поэтому кредиты по-прежнему отправляются Деннису): при возврате последовательности мы не останавливаемся до тех пор, пока не получим отрицательное значение (что оставляет нас с -1-м и -2-м элементом последовательности). Затем мы начинаем добавлять их перед печатью первого значения.
Это использует пару изящных лабиринт трюки в гольф. Давайте рассмотрим код в разделах:
IP начинается с движения
?
вправо (что читаетA
). На"
(без операции) он заходит в тупик, поэтому он поворачивается, выполняя?
снова (чтениеB
). Наконец,}
переходитB
на вспомогательный стек. Тупик сохраняет байт над наивнымТеперь цикл, который находит начало последовательности:
)(
(Прирост декремент) является не-оп, но это необходимо для того, чтобы верхняя часть стека положительна на стыке (например , что IP поворачивает на восток).:
дублируетA
,{
перемещаетB
обратно в основной стек,-
вычисляетA-B
. Что мы действительно хотимB-A
, так это`
отрицает ценность.Теперь это четырехсторонний перекресток. Для получения отрицательных результатов IP поворачивает влево
?
, читаяN
и переходя к следующей части программы. Если результат равен нулю, IP продолжает двигаться на юг, поворачивает в углу и остается в цикле. Если результат положительный, IP поворачивает направо (запад), поворачивает в углу и делает еще один поворот направо (снова на запад), поэтому он также остается в цикле. Я думаю, что это может стать распространенным шаблоном, позволяющим отличать отрицательные от неотрицательных (или положительных от не положительных) значений:По крайней мере, мне пока не удалось найти более компактный / полезный макет для этого случая.
В любом случае, пока
A
неотрицательный, цикл продолжается,}
перемещаетсяA
во вспомогательный стек и=
переставляетA
иB
.После того,
A
как отрицательный,?
читаетN
и мы переходим во второй цикл:Мы знаем, что
N
это положительно, поэтому мы можем рассчитывать на то, что IP повернет налево (на север). Тело цикла теперь просто:На словах: перемещает
N
иA
на вспомогательный стек. ДублируйтеB
, поменяйте местами копиюA
и добавьтеA
к другой копииB
. Дублируйте это снова, чтобы напечатать текущее значениеB
. Распечатать новую строку. ПереместитесьB
иN
вернитесь к основному стеку и уменьшите егоN
.В то время
N
как положительный, IP будет поворачивать направо (север), продолжая цикл. ДостигнувN
нуля, код завершается довольно причудливо:IP продолжает двигаться прямо (запад). В
?
пытается прочитать другое целое число, но мы уже достигли EOF, так что на самом деле толкает0
вместо этого.`
пытается отрицать это, но это все равно ноль. Таким образом, IP все еще движется на запад, поворачивает в углу, а затем продолжает двигаться вниз на тот,@
который завершает программу.Интересно, смогу ли я поместить их
@
в еще более дешевую позицию (в настоящее время она стоит 3 пробельных символа), превратив три"
из них`
в составные no-ops (вроде)(
), но я пока не смог сделать эту работу.источник
C
105102100 байтСпасибо @ C0deH4cker за вывод 2 байта!
Попробуйте онлайн на Ideone .
источник
Matlab / Octave, 115
125байтФункция должна называться как
f([8 13],10)
.Пример (Matlab):
Или попробуйте онлайн (октава) .
источник
f([a b],n)
должно быть разрешено.x=f(x,n)
значение заголовок функции ...Haskell,
67 6556 байтСпасибо @nimi за предложения
Это определяет троичную инфиксную функцию
%
, которая вызывается в формате(n%a)b
, например:объяснение
Бинарная функция инфиксным
#
, определенная на первой линии, принимает два целых числаa
иb
возвращает бесконечной Фибоначчи-подобные последовательности , гдеa
иb
происходят в следующих друг за другом элементов.Функция
%
просто берет первыеn
элементыa#b
.источник
let f=a:scanl(+)(a+b)f in f
(-> full#
:a#b|a>b=let f=a:scanl(+)(a+b)f in f|1>0=(b-a)#a
и сохранить два байта.> <>,
3331 + 1 для -v = 32 байтаВходные данные должны быть помещены в стек с использованием -v, поскольку синтаксический анализ десятичных чисел является нетривиальным в> <>.
Пояснение:
Я буду представлять стек после каждой (группы) операций. Начинается с [F (n), F (n + 1), N]
Первые строки идут вниз по серии к 0-му сроку:
Вторая строка идет вверх по серии, пока не напечатает N терминов:
источник
00.
в первой строке значение&
. Теоретически,!
должно работать, но я думаю, что> <> дополняет ширину строк до ширины самой длинной (правка: именно поэтому я полагаю, что вы имели00.
в первую очередь).!
или?
(в конце строки), если он находится на самой длинной строке. Вы можете попробовать это с чем-то вроде1n!
этого, иlorumipsum
это приведет к ошибке, но если под ним есть строка с чем-то длиннее, чем, например , это не будет.Джава,
1137876 байтБлагодарим ETHproduction за предоставленный алгоритм, который я использую в этом ответе.
Попробуй здесь .
Объяснение:
Оригинальный подход,
11393 байтаВыглядит больше в гольфе;)
Попробуйте это здесь .
Объяснение:
источник
b=b-a
доb-=a
, и то же самое сa=b+a
. Это сэкономит 2 байтаJavascript (ES6),
837363 байтаЭто могло бы быть в гольф по максимуму. Посмотрим.
Ungolfed:
источник
Mathematica 112
Будет ли это гольф в конце концов
источник
CJam, 40 байт
Шаги малыша. Это моя первая CJam-программа, и я горжусь тем, что она работает.
Он принимает данные в той же форме, что и в примерах.
Теперь я видел, что могу уменьшить его до 33 байт, используя
{ ... }*
конструкцию.И я мог бы даже уменьшить его еще на один, используя троичный оператор для очистки стека и выдачи ошибки.
источник
Рубин, 141 байт
выполнение
Функция f выдает желаемый результат, имена аргументов совпадают с именами переменных из вопроса
Ничего умного
источник
Mathematica, 59 байт
источник
Руби,
817573Сокращается на 6 байт при замене цикла for на range.map
Сохранены еще 2 байта путем перемещения выписки
источник
Пайк, 24 байта (неконкурирующий)
Попробуй это здесь!
источник
Желе , 14 байт
Попробуйте онлайн!
источник
Common Lisp, 91 байт
Попробуйте онлайн!
источник