Yalnızca toplama ve çıkarma kullanarak x'e kadar olan tüm kareleri hesaplayın


11

Amaç xtoplama ve çıkarma ile kadar tüm kareler hesaplamaktır .

Kurallar:

  1. Kod, oluşturulacak toplam kare sayısını alan ve tüm bu kareleri içeren bir dizi döndüren bir işlev olmalıdır.
  2. Sen olabilir değil kareler hesaplanması için dizeleri, yapılar, çarpma, bölme, veya fonksiyonlar yerleşik kullanın.
  3. Sadece diziler, tamsayılar (tam sayılar), toplama, çıkarma kullanabilirsiniz. Başka operatöre izin verilmiyor!

Bu bir sorusudur, bu yüzden bayttaki en kısa kod kazanır!


Bu aslında kareleri arttırmak için en optimize algoritmadır - ya da en azından hemen hemen aynı cevapları alır.
Peter Taylor

2
@PeterTaylor Hayır, aynı değil, çünkü kareleri artırmak için en optimize algoritma, ama sorum sadece toplama ve çıkarma istiyor.
Diş fırçası

Hangisi aynı şey. Tanık olarak: bu soruya verilen mevcut cevap, bir önceki soruya verilen cevapların büyük çoğunluğu ile aynıdır.
Peter Taylor

@PeterTaylor Taraflı olabilirim, ama gerçekten aynı olduğunu düşünmüyorum.
Diş fırçası

3
Bu sorunun başka bir yerde zaten cevapları olabilir, ancak bu soruyu diğer sorunun bir kopyası haline getirmez .
Blacklight Shining

Yanıtlar:



6

C, 55 52 bayt

int s(int n,int*r){for(int i=0,j=-1;n--;*r++=i+=j+=2);}

sadece tek sayıları toplar

  • n: hesaplanacak kare sayısı
  • r: sonuçları depolamak için çıktı dizisi
  • j: ardışık değerleri 1, 3, 5, 7, alır ...
  • i: jher yinelemede artırılır

Düzenle

Örtülü int bildirimi (> C99) kullanılarak 4 karakter kaydedilebilir, ancak forbaşlatıcılar> C99'da bir bildirim içeremediğinden bu 1 karaktere mal olur . Sonra kod

s(int n,int*r){int i=0,j=-1;for(;n--;*r++=i+=j+=2);}

kullanım

void main() {
    int r[20];
    s(20, r);
    for (int i = 0; i < 20 ; ++i) printf("%d\n", r[i]);
}  

Çıktı

1
4
9
16
25
36
49
(...)
361
400

1
bu mantık mükemmel! +1 hak ediyorsun
Mukul Kumar

5

GolfScript, 17 karakter

{[,{.+(1$+}*]}:F;

Kullanım (ayrıca çevrimiçi örneklere bakın ):

10 F     # => [0 1 4 9 16 25 36 49 64 81]

Not: * çarpma operatörü değil, bir döngüdür.


TAMAM; o nasıl çalışır?
Diş fırçası

@toothbrush girdiyi ,alır ve diziye dönüştürür [0 1 ... n-1]. Sonra *verilen kod bloğunu diziye enjekte eder. Bu blok ilk olarak geçerli öğeyi ( .+) iki katına çıkarır (ve ardından bir önceki sonucu ekler 1$+(başka bir deyişle, 2j-1önceki kare numarasına ekler ). []yeni bir dizi döndürmek için her şeyi içine alır.
Howard

Harika! GolfScript'i bilmiyorum, bu yüzden nasıl çalıştığını merak ettim.
Diş fırçası

5

Windows Toplu İş, 115 bayt

setlocal enabledelayedexpansion&for /l %%i in (1 1 %1)do (set a=&for /l %%j in (1 1 %%i)do set /a a+=%%i
echo.!a!)

Bu, cmd'den çalıştırılmak yerine bir toplu iş dosyasına yerleştirilmelidir ve listeyi konsola gönderir. İlk komut satırı bağımsız değişkeninden oluşturulacak kare sayısını alır. Çoğunlukla &satırsonu yerine kullandığı için , yine de bir tanesine ihtiyaç vardır ve iki bayt olarak sayılır.

Gecikmeli değişken genişleme etkin, bu ile yapılabilir cmd /v:on. Değilse setlocal enabledelayedexpansion&, başlangıçta ekstra bir ihtiyaç vardı (komut dosyası olmadan 83 bayt).


4

Haskell - 30

f n=scanl1(\x y->x+y+y-1)[1..n]

Bu gerçeği kullanır (n+1)^2=n^2+2n+1


4

Perl, 27 bayt

sub{map{$a+=$_+$_-1}1..pop}

Matematik:

Matematik

10 kare yazdırmak için işlevi çağırmak için komut dosyası:

#!/usr/bin/env perl
$square = sub{map{$a+=$_+$_-1}1..pop};
use Data::Dumper;
@result = &$square(10);
print Dumper \@result;

Sonuç:

$VAR1 = [
          1,
          4,
          9,
          16,
          25,
          36,
          49,
          64,
          81,
          100
        ];

Düzenlemeler:

  • Anonim işlev (−2 bayt, teşekkürler skibrianski )
  • popyerine shift(−2 bayt, teşekkürler skibiranski )

Alt adınızı adlandırmanız için hiçbir neden göremiyorum. IOW "sub {map {$ a + = $ _ + $ _- 1} 1..shift}" bana yasal geliyor ve size iki karakter kaydediyor.
skibrianski

@skibrianski: Anonim bir işlev de bir işlevdir. Dezavantajı, fonksiyonun çağrılması biraz daha hantal.
Heiko Oberdiek

Doğru, ama arayan kişi. Diğer dillerde anonim subs tanımlayan girişleri var, bu yüzden güvenli olduğunu düşünüyorum =)
skibrianski

Üstelik tek bir argüman olduğundan shift () yerine pop () kullanarak 2 karakter daha kaydedebilirsiniz.
skibrianski

@skibrianski: Doğru, teşekkürler.
Heiko Oberdiek

4

JavaScript - 32 Karakter

for(a=[k=i=0];i<x;)a[i]=k+=i+++i

Bir değişkenin xvar olduğunu varsayar ve adeğerler için bir kareler dizisi oluşturur 1..x.

ECMAScript 6 - 27 Karakter

b=[f=i=>b[i]=i&&i+--i+f(i)]

Çağrı f(x), diziyi bdeğerler için karelerle dolduracaktır 0..x.


Sormak zorundayım ... i+++isonunda ...?
WallyWest

2
k+=i+++iaynı k += i + (++i)şekilde aynı olan k+=i+i+1, ardındani=i+1
MT0

Oh bu deha ... Gerektiğinde bir sonraki codegolf'umda bunu uygulamak zorundayım! :)
WallyWest

İşlev bildirimini dizinin içine (örneğin b=[f=i=>b[i]=i&&i+--i+f(i)]) taşıyarak bir karakter kaydedebilirsiniz .
Diş fırçası

Teşekkürler - bir nokta üst üste kaldırmak için bir şeyleri hareket ettirerek üst cevap bir karakter de kaydetti.
MT0

4

Julia - 33

Herhangi bir kare numarası tek sayıların toplamı ile yazılabilir:

julia> f(x,s=0)=[s+=i for i=1:2:(x+x-1)];f(5)
5-element Array{Int64,1}:
  1
  4
  9
 16
 25

Merhaba, CG.se'ye hoş geldiniz! Güzel, kısa ve öz bir cevap. Julia'yı hiç duymadım, ama ilginç görünüyor.
Jonathan Van Matre

Julia'da "2x" çarpma değil mi? Bunun yerine x + x diyebilirsiniz, bu size sadece bir bayta mal olur.
Glenn Randers-Pehrson

Haklısın (fark etmedin), düzenlendi.
ÇKP

Julia'yı henüz bilmiyorum, ancak docs.julialang.org/en/release-0.2 adresindeki çevrimiçi kılavuzda aradım ve "Sayısal Değişmez Katsayılar: Ortak sayısal formülleri ve ifadeleri daha net hale getirmek için Julia değişkenlere izin veriyor hemen önünde çarpma anlamına gelen sayısal bir değişmez olur. " Evet, 2x çarpmadır.
Glenn Randers-Pehrson

2

C ++ 99 81 78 80 78

int* f(int x){int a[x],i=1;a[0]=1;while(i<x)a[i++]=a[--i]+(++i)+i+1;return a;}  

Code-Golf'teki ilk denemem

Bu kod dayanan
bir = 2 xn - 1
burada n terimi sayısı ve bir olduğu , n dizi aşağıdaki inci terimi
1, 3, 5, 9, 11, 13, .....
ilk 2 açısından = 2 toplamı kare

ilk 3 terimin toplamı = 3 kare
vb.


2
Bence döngüden {}sonra parantezleri kaldırabilirsiniz for, çünkü sadece bir ifade var. Bu, char sayınızı 2 azaltabilir
user12205

1
Main () dışında bir işlevde sabit olmayan boyutta diziler
bildirirseniz

1
Bu kod tanımsız bir davranışa sahip.
Kerrek SB

1
ve dönüş sırasında yok edilen yığın üzerindeki verilere işaretçiyi döndürür.
VX

1
@MukulKumar addition, subtraction, sadece bunları kullanıyorum
mniip

2

DCPU-16 Düzeneği (90 bayt)

Bunu kurgusal bir işlemci için derlemede yazdım, çünkü neden olmasın?

:l
ADD I,1
SET B,0
SET J,0
:m
ADD J,1
ADD B,I
IFL J,I
SET PC,m
SET PUSH,B
IFL I,X
SET PC,l

Sayının X kaydında olması ve diğer kayıtların 0 olması beklenir. Sonuçlar yığına aktarılır, 16 bit mimari nedeniyle 65535'e ulaştığında kırılır. SUB PC, 1Test etmek için sonuna bir eklemek isteyebilirsiniz . Derlendi, program 20 bayt (10 kelime) olmalıdır.


2

Haskell

f x=take x [iterate (+y) 0 !! y | y<- [0..]]

Bu temel olarak çarpımı icat eder, kendi başına kullanır ve tüm sayılarla eşler. f 10= [0,1,4,9,16,25,36,49,64,81]. Ayrıca f 91= [0,1,4,9,16,25,36,49,64,81,100,121,144,169,196,225,256,289,324,361,400,441,484,529,576,625,676,729,784,841,900,961,1024,1089,1156,1225,1296,1369,1444,1521,1600,1681,1764,1849,1936,2025,2116,2209,2304,2401,2500,2601,2704,2809,2916,3025,3136,3249,3364,3481,3600,3721,3844,3969,4096,4225,4356,4489,4624,4761,4900,5041,5184,5329,5476,5625,5776,5929,6084,6241,6400,6561,6724,6889,7056,7225,7396,7569,7744,7921,8100].


Demoyu 10'dan biraz daha uzatabilir misiniz?
Glenn Randers-Pehrson

2

Haskell, 34/23

n#m=m+n:(n+2)#(m+n)
f n=take n$1#0

veya ithalatta sorun yoksa:

f n=scanl1(+)[1,3..n+n]

Çıktı:

λ> f 8
[1,4,9,16,25,36,49,64]

1

Javascript 47

function f(n,a){return a[n]=n?f(n-1,a)+n+n-1:0}

r=[];f(12,r);console.log(r) İadeler :
[0, 1, 4, 9, 16, 25, 36, 49, 64, 81, 100, 121, 144]


Harika! In ECMAscript 6: f=(n,a)=>a[n]=n?f(n-1,a)+n+n-1:0.
Diş fırçası

1
ECMAScript 6'nın gerçekten genel kullanıma girmesini bekleyemiyorum. Bunu öğrenmek için mükemmel bir bahane olurdu.
Isiah Meadows

1
ECMAScript 6 spesifikasyonunun Ok Fonksiyon kısmı, sürüm 22'den beri
FireFox'ta

1

Smalltalk, 52

f:=[:n||s|(s:=1)to:n collect:[:i|x:=s.s:=s+i+i+1.x]]

Yeni bir dizi döndürür (yani varolan bir diziyi doldurmaz veya eklemez).

aramak:

f değeri: 10

-> # (1 4 9 16 25 36 49 64 81100)


1

piton - 39

a=0
for i in range(5):a+=i+i+1;print(a)

5Herhangi bir değerle değiştirin . Herhangi bir öneri?


1

Bash - 92 85 62 61 59 57

declare -i k=1;for((i=0;i++<$1;k+=i+i+1));do echo $k;done

Sonuç:

$ ./squares.sh 10
1
4
9
16
25
36
49
64
81
100

Düzenleme: Ben iç döngü @ mniip Haskell çözüm algoritması ile değiştirildi.


1

APL ve J'de yukarıdakiyle aynı yöntem:

APL: F←{+\1+V+V←¯1+⍳⍵}(17 karakter) çoğu APL varyantıyla çalışır ( burada deneyin )

NGN APL ile daha da az (sadece 14 karakter): F←{+\1+V+V←⍳⍵}( buraya bakın )

J: f=:+/\@(>:@+:@:i.)(18 karakter)

edit: APL'de daha iyi çözüm: F←{+\¯1+V+V←⍳⍵}(15 karakter)


1

C # (82)

int[] s(int n){int i,p=0;var r=new int[n];while(i<n){p+=i+i+1;r[i++]=p;}return r;}

1

C # - 93

int[]s(int l){int[]w=new int[l];while(l>=0){int i=0;while(i<l){w[l-1]+=l;i++;}l--;}return w;}

Aynı sınıfın başka bir yönteminden çağrıldığında, dizi, - öğeye [1,4,9,16,25,36...]kadar döndürür l.


Eğer arasında boşluk kaldırmayı deneyin vermedi int[]ve sq? C # bilmiyorum, ama bence işe yaramalı.
user12205

Hayır, işe yaramayacak. İlk int [] yöntemi "sq" yönteminin dönüş türüdür. Yöntem adını sadece "s" olarak azaltabilirim :)
Rajesh

Yani int[]sqyerine int[] sqve int[]resyerine kullanmak int[] res. Bu, iki karakter kaydetmenize yardımcı olur ve bununla ilgili herhangi bir derleme hatası almadım. Ayrıca önerdiğiniz sqve resönerdiği gibi tek karakter tanımlayıcıları kullanmalısınız .
user12205

Cevabınızla ilgili bir sorun var gibi görünüyor
user12205

Monospace fontlu bir kod bloğuna koymak için kodu 4 boşlukla girinti yapın.
luser droog

1

Fortran II | IV | 66 | 77, 134 122 109 105

  SUBROUTINES(N,M)
  INTEGERM(N)
  K=0
  DO1I=1,N
  K=K+I+I-1
1 M(I)=K
  END

Düzenleme: iç döngü kaldırıldı ve bunun yerine @ mniip'in Haskell algoritması kullanılır.

Düzenleme: Altyordam ve sürücünün geçerli Fortran II ve IV olduğu doğrulandı

Sürücü:

  INTEGER M(100)
  READ(5,3)N
  IF(N)5,5,1
1 IF(N-100)2,2,5
2 CALLS(N,M)
  WRITE(6,4)(M(I),I=1,N)
3 FORMAT(I3)
4 FORMAT(10I6)
  STOP  
5 STOP1
  END

Sonuç:

$ echo 20 | ./a.out
   1     4     9    16    25    36    49    64    81   100
 121   144   169   196   225   256   289   324   361   400

mniip, teşekkürler, iç döngümü kodunla değiştirdim.
Glenn Randers-Pehrson

1

Python - 51

Burada kuralların istediği gibi bir işlev tanımlıyorum.

Kullanılması sumtek sayı:

f=lambda n:[sum(range(1,i+i+3,2))for i in range(n)]

Bu yalnızca sum(toplama yapan bir yerleşik) ve range(toplama kullanarak diziler oluşturan bir yerleşik) kullanır. Buna itiraz ederseniz sum, bunu aşağıdakilerle yapabiliriz reduce:

def g(n):v=[];reduce(lambda x,y:v.append(x) or x+y,range(1,i+i+3,2));return v

1

PHP, 92 bayt

Bunun, "kısa etiketler" seçeneğinin etkinleştirilmiş olması gerekir (başlangıçta 3 bayt tıraş etmek için).

<? $x=100;$a=1;$r=0;while($r<=$x){if($r){echo"$r ";}for($i=0,$r=0;$i<$a;$i++){$r+=$a;}$a++;}

Çıktı:

1 4 9 16 25 36 49 64 81 100 

1

İleri - 48 bayt

: f 1+ 0 do i 0 i 0 do over + loop . drop loop ;

Kullanımı:

7 f

Çıktı:

0 1 4 9 16 25 36 49
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.