Переменная последовательность знаков

16

Вступление

Признак ряда является либо +, или -для каждого ненулевого целого числа. Ноль сам по себе без знака (так +0же, как -0). В следующей последовательности мы будем чередовать положительный знак , ноль и отрицательный знак . Последовательность начинается с 1, поэтому мы пишем 1с положительным знаком, с нуля (это странно, но мы просто умножаем число на 0) и отрицательным знаком:

1, 0, -1

Следующий номер 2, и мы снова делаем то же самое:

2, 0, -2

Последовательность в конечном итоге такова:

1, 0, -1, 2, 0, -2, 3, 0, -3, 4, 0, -4, 5, 0, -5, 6, 0, -6, 7, 0, -7, ...

Или более читаемая форма:

a(0) = 1
a(1) = 0
a(2) = -1
a(3) = 2
a(4) = 0
a(5) = -2
a(6) = 3
a(7) = 0
a(8) = -3
a(9) = 4
...

Задание

Если задано неотрицательное целое число n , выведите n- й член вышеуказанной последовательности. Вы можете выбрать, будете ли вы использовать индексированные нулями или одноиндексированные версию .

Тестовые случаи:

Zero-индексируются:

a(0) = 1
a(11) = -4
a(76) = 0
a(134) = -45
a(296) = -99

Или, если вы предпочитаете одноиндексный:

a(1) = 1
a(12) = -4
a(77) = 0
a(135) = -45
a(297) = -99

Это , поэтому выигрывает представление с наименьшим количеством байтов!

Аднан
источник
Это нормально, если вы начнете с[0, 0, 0, -1, 0, 1...
Blue
@muddyfish нет извините, это должно начаться с 1.
Аднан

Ответы:

6

JavaScript ES6, 18 байт

n=>-~(n/3)*(1-n%3)

Получилось очень похоже на ответ @ LeakyNun, но я его не видел, пока не опубликовал свой.

Объяснение и Унгольфед

-~является сокращением Math.ceilили округлением:

n =>               // input in var `n`
    Math.ceil(n/3) // Get every 3rd number 1,1,1,2,2,2, etc.
    *
    (1-n%3)        // 1, 0, -1, 1, 0, -1, ...

Downgoat
источник
1
(Настоящим я подтверждаю, что он не видел моего решения до того, как опубликовал свое решение)
Leaky Nun
Math.ceilи -~разные; Math.ceil(1) == 1тогда как-~1 == 2
Cyoce
1
На 1 байт короче:n=>~(n/3)*~-(n%3)
Cyoce
6

MarioLANG, 93 81 байт

один индексированные

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

;(-))+(-
"============<
>:(![<:![<:)![
 !=#="!#="!=#=
!  < !-< !- <
#==" #=" #=="

Пояснение:

мы начнем с принятия импульса

;

который дает нам

          v
... 0 0 input 0 0 ...

затем мы уменьшаем левый байт и увеличиваем правый байт с помощью

;(-))+(
=======

мы заканчиваем с

           v
... 0 -1 input +1 0 ...

Затем мы создали цикл

;(-))+(-
"============<
>  ![< ![<  ![
   #=" #="  #=
!  < !-< !- <
#==" #=" #=="

цикл будет идти, пока память не будет выглядеть

         v 
... 0 -X 0 +X 0 ...

тогда нам нужно только вывести результат

;(-))+(-
"============<
>:(![<:![<:)![
 !=#="!#="!=#=
!  < !-< !- <
#==" #=" #=="
Эфир лягушка
источник
2
Ницца! Вам, кажется, нравится MarioLang.
Rɪᴋᴇʀ
@EasterlyIrk Чувство не кажется взаимным от MarioLang к EtherFrog, хотя: ;(и >:(. Хотя два раза [<:можно было бы считать слегка счастливыми. ; P
Кевин Круйссен
4

Python 2, 24 байта

lambda n:(n/3+1)*(1-n%3)

Полная программа:

a=lambda n:(n/3+1)*(1-n%3)

print(a(0))   #   1
print(a(11))  #  -4
print(a(76))  #   0
print(a(134)) # -45
print(a(296)) # -99
Пропитанная монахиня
источник
4

MATL, 15 12 байт

3/XkG3X\2-*_

Это использует одну основанную индексацию.

Попробуйте онлайн! или проверить контрольные примеры

Объяснение:

    G          #Input
     3X\       #Modulus, except multiples of 3 give 3 instead of 0
        2-     #Subtract 2, giving -1, 0 or 1
3/Xk           #Ceiling of input divided by 3.
          *    #Multiply 
           _   #Negate
DJMcMayhem
источник
Чтобы решить большинство вопросов, что-то вроде Q3/Xk-1:1G_)*может работать лучше. Вероятно, вместо этого он может быть изменен для индексации на основе 1.
Suever
4

Haskell, 27 байт

f x=div(x+3)3*(1-mod(x+3)3)

Чуть более интересное 28-байтовое решение:

(((\i->[i,0,-i])=<<[1..])!!)

(Оба 0индексируются)

Майкл Кляйн
источник
3

MATL , 8 байт

:t~y_vG)

Результат основан на 1.

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

объяснение

Это строит массив 2D

 1  2  3  4  5 ...
 0  0  0  0  0 ...
-1 -2 -3 -4 -5 ...

а затем использует линейное индексирование, чтобы извлечь нужный термин. Линейная индексация означает индекс вниз, затем через (так что в приведенном выше массиве первые записи в линейном порядке являются 1, 0, -1, 2, 0, ...)

:     % Vector [1 2 ... N], where N is implicit input
t~    % Duplicate and logical negate: vector of zeros
y_    % Duplicate array below the top and negate: vector [-1 -2 ... -N]
v     % Concatenate all stack contents vertically
G)    % Index with input. Implicit display
Луис Мендо
источник
3

Perl 5, 22 байта

21 плюс один для -p:

$_=(-$_,$_+2)[$_%3]/3

Использует индексирование на основе 1.

Объяснение:

-pустанавливает переменную, $_равную вводу. Затем код устанавливает его равным $_%3элементу th, разделенному на 3, из списка на основе 0 (-$_,$_+2)(где %по модулю). Обратите внимание, что если $_%3равно два, то такого элемента нет, и последующее деление на 3 нумерует неопределенное значение до 0. -pЗатем печатается $_.

msh210
источник
3

Баш, 28 25 байт

echo $[(1+$1/3)*(1-$1%3)]
rexkogitans
источник
@DigitalTrauma, tkx, не знал этого ...
rexkogitans
2

Perl 6 ,  26  23 байта

{({|(++$,0,--$)}...*)[$_]}
{($_ div 3+1)*(1-$_%3)}

(Короче был переведен из других ответов)

Пояснение (первого):

{ # bare block with implicit parameter 「$_」
  (

    # start of sequence generator

    { # bare block
      |(  # slip ( so that it flattens into the outer sequence )
        ++$, # incrementing anon state var =>  1, 2, 3, 4, 5, 6
        0,   # 0                           =>  0, 0, 0, 0, 0, 0
        --$  # decrementing anon state var => -1,-2,-3,-4,-5,-6
      )
    }
    ...  # repeat
    *    # indefinitely

    # end of sequence generator

  )[ $_ ] # get the nth one (zero based)
}

Тестовое задание:

#! /usr/bin/env perl6
use v6.c;
use Test;

# store it lexically
my &alt-seq-sign = {({|(++$,0,--$)}...*)[$_]}
my &short-one = {($_ div 3+1)*(1-$_%3)}

my @tests = (
    0 =>   1,
   11 =>  -4,
   76 =>   0,
  134 => -45,
  296 => -99,
  15..^30  => (6,0,-6,7,0,-7,8,0,-8,9,0,-9,10,0,-10)
);

plan @tests * 2 - 1;

for @tests {
  is alt-seq-sign( .key ), .value, 'alt-seq-sign  ' ~ .gist;

  next if .key ~~ Range; # doesn't support Range as an input
  is short-one(    .key ), .value, 'short-one     ' ~ .gist;
}
1..11
ok 1 - alt-seq-sign  0 => 1
ok 2 - short-one     0 => 1
ok 3 - alt-seq-sign  11 => -4
ok 4 - short-one     11 => -4
ok 5 - alt-seq-sign  76 => 0
ok 6 - short-one     76 => 0
ok 7 - alt-seq-sign  134 => -45
ok 8 - short-one     134 => -45
ok 9 - alt-seq-sign  296 => -99
ok 10 - short-one     296 => -99
ok 11 - alt-seq-sign  15..^30 => (6 0 -6 7 0 -7 8 0 -8 9 0 -9 10 0 -10)
Брэд Гилберт b2gills
источник
2

J, 19 15 байт

>.@(%&3)*1-3|<:

Наверное, нужно играть в гольф дальше ...

1-индексироваться.

Ungolfed:

>> choose_sign      =: 1-3|<:      NB. 1-((n-1)%3)
>> choose_magnitude =: >.@(%&3)    NB. ceil(n/3)
>> f                =: choose_sign * choose_magnitude
>> f 1 12 77
<< 1 _4 0

Где >>означает ввод (STDIN) и <<означает вывод (STDOUT).

Пропитанная монахиня
источник
2

Пайк, 8 7 байт (старая версия)

3.DeRt*

Попробуй это здесь! - Обратите внимание, что ссылка, вероятно, не будет длиться долго

3.D      - a,b = divmod(input, 3)
   e     - a = ~a -(a+1)
     t   - b -= 1
      *  - a = a*b
         - implicit output a

Новейшая версия

3.DhRt*_

Попробуй это здесь!

3.D      - a,b = divmod(input, 3)
   h     - a+=1
     t   - b-=1
      *  - a = a*b
       _ - a = -a
         - implicit output a
синий
источник
Можете ли вы предоставить ссылку на (старая версия)
Downgoat
Последний коммит, где старый код работает здесь (сегодня раньше)
Blue
2

J, 27 байт

Хотя это и не самое лучшее в гольфе, мне это нравится больше, так как оно использует повестку дня.

>.@(>:%3:)*1:`0:`_1:@.(3|])

Вот разложение этого дерева:

         ┌─ >.      
  ┌─ @ ──┤    ┌─ >: 
  │      └────┼─ %  
  │           └─ 3: 
  ├─ *              
──┤           ┌─ 1: 
  │      ┌────┼─ 0: 
  │      │    └─ _1:
  └─ @. ─┤          
         │    ┌─ 3  
         └────┼─ |  
              └─ ]  

Это очень похоже на J-ответ Кенни в том смысле, что он выбирает величину и знак, но отличается тем, что я использую повестку дня для выбора знака.

Конор О'Брайен
источник
2

MATL, 8 байт

_3&\wq*_

Это решение использует основанную на 1 индексацию в последовательности.

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

Модифицированная версия, показывающая все тесты

объяснение

        % Implicitly grab the input
_       % Negate the input
3&\     % Compute the modulus with 3. The second output is floor(N/3). Because we negated
        % the input, this is the equivalent of ceil(input/3)
w       % Flip the order of the outputs
q       % Subtract 1 from the result of mod to turn [0 1 2] into [-1 0 1]
*       % Take the product with ceil(input/3)
_       % Negate the result so that the sequence goes [N 0 -N] instead of [-N 0 N]
        % Implicitly display the result
Suever
источник
2

Pyth, 10 байт

*h/Q3-1%Q3

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

Объяснение:

*     : Multiply following two arguments
h/Q3  : 1 + Input/3
-1%Q3 : 1 - Input%3

Примечание: я принял последовательность с нулевым индексом.

Джон Ред
источник
1
Вы, вероятно, хотели бы включить эту ссылку. Кроме того, добро пожаловать в PPCG!
Дрянная Монахиня
Я очень близко подошел к вашему решению ...*@(1ZtZ)%Q3h/Q3
FliiFe
@FliiFe (1ZtZ)=-L1 2
монахиня
2

На самом деле, 10 байтов

3@│\u)%1-*

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

Объяснение:

3@│\u)%1-*
3@│         push 3, swap, duplicate entire stack ([n 3 n 3])
   \u)      floor division, increment, move to bottom ([n 3 n//3+1])
      %1-   mod, subtract from 1 ([1-n%3 n//3+1])
         *  multiply ([(1-n%3)*(n//3+1)])
Mego
источник
2

05AB1E, 7 байтов

Код:

(3‰`<*(

Разъяснение:

(           # negate input: 12 -> -12
 3‰         # divmod by 3: [-4, 0]
   `        # flatten array: 0, -4
    <       # decrease the mod-result by 1: -1, -4
     *      # multiply: 4
      (     # negate -4
Emigna
источник
2

GeoGebra, 44 байта

Element[Flatten[Sequence[{t,0,-t},t,1,n]],n]

где n одноиндексное.

Объяснение:

Element[                      , n] # Return the nth element of the list                  .
 Flatten[                    ]     # Strip all the unnecessary braces from the list     /|\
  Sequence[{t,0,-t}, t, 1, n]      # Generate a list of lists of the form {t, 0, -t}     |
                             # This list will start with {1,0,-1} and end with {n,0,-n}  |

Нет необходимости генерировать все триплеты до конца {n, 0, -n}, но это короче, чем запись ceil(n/3)или что-то в этом роде. Обратите внимание, что он nдолжен быть определен для создания этого объекта (если он не был определен во время его запуска, GeoGebra предложит вам создать слайдер n).

Джо
источник
Привет и добро пожаловать в PPCG! У вас есть ссылка, по которой я могу это проверить (желательно онлайн)?
Rɪᴋᴇʀ
@ EᴀsᴛᴇʀʟʏIʀᴋ, спасибо! Вот ссылка на онлайн-апплет thingamabob. Некоторое время страница выглядела пустой, но потом она появилась.
Джо
О, круто. Но как, где я могу положить в формулу? > _> Я попытался вставить его в пустую строку, и он предложил создать слайдер, но больше ничего не произошло.
Rɪᴋᴇʀ
@ EᴀsᴛᴇʀʟʏIʀᴋ: С левой стороны, где написано «Ввод ...» Сначала, для инициализации n, введите что-то вроде n=297(это даст вам слайдер, который настроен хорошо). Затем вставьте формулу в поле ввода, которое теперь должно быть ниже n. (Удостоверьтесь, что нажали return;) Формула должна соответствовать тому nчлену последовательности, и она должна измениться при перемещении ползунка.
Джо
2

Лабиринт , 17 15 14 байтов

Сохранено 3 байта, используя идею Сок 1-(n%3)вместо использования ~(n%3-2).

1?:#/)}_3%-{*!

Программа завершается с ошибкой (деление на ноль), но сообщение об ошибке отправляется в STDERR.

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

объяснение

Программа полностью линейна, хотя в конце код выполняется наоборот.

1     Turn top of stack into 1.
?:    Read input as integer and duplicate.
#     Push stack depth (3).
/)    Divide and increment.
}     Move over to auxiliary stack.
_3%   Take other copy modulo 3.
-     Subtract from 1. This turns 0, 1, 2 into 1, 0, -1, respectively.
{*    Move other value back onto main stack and multiply.
!     Output as integer.

Указатель инструкции теперь попадает в тупик и оборачивается, поэтому он начинает выполнять код с конца:

*     Multiply two (implicit) zeros.
{     Pull an (implicit) zero from the auxiliary to the main stack.
-     Subtract two (implicit) zeros from one another.
      Note that these were all effectively no-ops due to the stacks which are
      implicitly filled with zeros.
%     Attempt modulo, which terminates the program due to a division-by-zero error.
Мартин Эндер
источник
2

Эрланг, 40 байт

F=fun(N)->trunc((N/3+1)*(1-N rem 3))end.

К сожалению, у Эрланга нет оператора «%» по модулю, а «rem» требует пробелов, даже до 3.

fxk8y
источник
2

Гексагония , 25 байтов

?'+}@/)${':/3$~{3'.%(/'*!

Или в не минимизированном формате:

    ? ' + }
   @ / ) $ {
  ' : / 3 $ ~
 { 3 ' . % ( /
  ' * ! . . .
   . . . . .
    . . . .

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

Мой первый набег на Гексагонию, так что я уверен, что я не сделал это нигде настолько эффективно, как это могло бы быть сделано ...

Вычисляет -(n%3 - 1)на одном ребре памяти, n/3 + 1на соседнем, а затем умножает их вместе.

Sok
источник
Вау, очень интересно это увидеть! :)
Аднан
2

R, 28 байт

-((n=scan())%%3-1)*(n%/%3+1)

Похоже, это вариация большинства ответов здесь. Ноль на основе.

   n=scan()                  # get input from STDIN
  (        )%%3-1            # mod by 3 and shift down (0,1,2) -> (-1,0,1)
-(               )           # negate result (1,0,-1), this handles the alternating signs
                  *(n%/%3+1) # integer division of n by 3, add 1, multiply by previous

Приятно то, что он обрабатывает несколько входов

> -((n=scan())%%3-1)*(n%/%3+1)
1: 0 3 6 9 1 4 7 10 2 5 8 11
13: 
Read 12 items
 [1]  1  2  3  4  0  0  0  0 -1 -2 -3 -4
> 

Первоначально я хотел сделать следующее, но не мог обрезать лишние байты.

rbind(I<-1:(n=scan()),0,-I)[n]

Используется rbindдля добавления нулей и отрицательных значений в диапазон от 1 до nвозврата nпервого числа (на основе одного).

# for n = 5
rbind(                    )    # bind rows 
            n=scan()           # get input from STDIN and assign to n
      I<-1:(        )          # build range 1 to n and assign to I
                     ,0        # add a row of zeros (expanded automatically)
                       ,-I     # add a row of negatives
                           [n] # return the n'th term
MickyT
источник
2

Пакет (Windows), 86 байт

Alternate.bat

SET /A r=%1%%3
SET /A d=(%1-r)/3+1
IF %r%==0 ECHO %d%
IF %r%==1 ECHO 0
IF %r%==2 ECHO -%d%

Эта программа работает как Alternate.bat nгде nномер , который вы хотите вызвать функцию на.

Дрю Кристенсен
источник
2

APL, 12 символов

-×/1-0 3⊤6+⎕

0 3⊤это APL divmod 3.

lstefano
источник
2

Ява 7, 38 37 36 байт

Мой первый гольф, будь нежным

int a(int i){return(1+i/3)*(1-i%3);}

Попробуй это здесь!(тестовые случаи включены)

Редактировать: я не учел, а также ударил еще одного персонажа, заменив (-i%3+1)на (1-i%3).

Стивен Х.
источник
1
Здравствуйте и добро пожаловать в PPCG! Вы можете удалить пробел после returnи использовать лямбду Java 8.
NoOneIsHere
Я должен указать, что это была Java 7. Я удалю это место, хотя. Благодарность!
Стивен Х.
1

MATLAB / Octave, 27 байт

@(n)ceil(n/3)*(mod(-n,3)-1)

Это создает анонимную функцию, которая может быть вызвана с помощью ans(n) . В этом решении используется индексирование на основе 1.

Все тесты

Suever
источник
1

Mathematica 26 байтов

С 4 байтами сохранено благодаря Мартину Эндеру.

⎡#/3⎤(-#~Mod~3-1)&

Использует тот же подход, что и Suever.

DavidC
источник
1

Октава, 23 байта

Без модов минусов ...

@(n)(-[-1:1]'*[1:n])(n)

Использует основанную на 1 магии индексации.


объяснение

Создает анонимную функцию, которая будет:

(-[-1:1]'*[1:n])(n)
  [-1:1]              % make a row vector [-1 0 1]
 -      '             % negate and take its transpose making a column vector
          [1:n]       % make a row vector [1..n], where n is the input
         *            % multiply with singleton expansion
               (n)    % use linear indexing to get the nth value

После шага умножения у нас будет матрица 3xn, например, так (для n = 12):

 1    2    3    4    5    6    7    8    9   10   11   12
 0    0    0    0    0    0    0    0    0    0    0    0
-1   -2   -3   -4   -5   -6   -7   -8   -9  -10  -11  -12

Создание nстолбцов - это излишне, но это удобное число, которое гарантированно будет достаточно большим. Линейное индексирование отсчитывает каждый столбец слева направо, поэтому элемент с линейным индексом 4будет 2.

Все тестовые случаи на ideone .

мерный стакан
источник
1

постоянный ток, 10

?2+3~1r-*p

Использует индексирование на основе 1.

?              # Push input to stack
 2+            # Add 2
   3~          # divmod by 3
     1r-       # subtract remainder from 1
        *      # multiply by quotient
         p     # print
Цифровая травма
источник