Tambahkan dan gandakan angka yang membingungkan

16

The nomor split-kompleks , juga dikenal sebagai "nomor perplex" yang mirip dengan nomor kompleks. Alih-alih i^2 = -1, bagaimanapun, kita punya j^2 = 1; j != +/-1. Setiap angka berbentuk z = x + j*y.

Dalam satu upaya untuk membatasi kompleksitas tantangan ini, saya akan menggunakan simbol -untuk mewakili negasi, karena tidak akan ada pengurangan.

Berikut adalah beberapa contoh untuk kesenangan menonton Anda:

6 * 9 = 54            // real numbers still act normally
5 + -7 = -2
j*1 + j*1 = j*2           // two `j`s added together make a j*2
7 * j*1 = j*7           // multiplication is commutative & associative
j*1 + 2 = 2+j*1           // like oil and water, "combine" to form a split-complex number
j*1 + j*-3 = j*-2          // seems okay so far
j*j*1 = j*-1*j*-1 = 1     // kinda sketchy, but such is its inherent nature
j*j*-1 = j*-1*j*1 = -1  
(2+j*3)+(4+j*7) = 6+j*10  // combine like terms
7 * (2+j*3) = 14+j*21 // distributive property
j * (2+j*3) = (j*2) + (j*j*3) = 3+j*2   // since j^2 = 1, multiplying my j "swaps" the coefficients
(2+j*3)*(4+j*7) = (2*4)+(2*j*7)+(j*3*4)+(j*3*j*7) = 8+j*14+j*12+21 = 29+j*26 // a complete multiplication

Tantangan

Tujuan dari tantangan ini adalah untuk mengevaluasi ekspresi dengan bilangan kompleks.

Ini adalah kode-golf, byte paling sedikit menang.

Memasukkan

Input akan menjadi satu baris yang hanya berisi simbol +*()-, digit 0123456789, dan huruf j, dengan baris baru opsional. String ini mewakili ekspresi, menggunakan notasi infiks dan prioritas operator (perkalian sebelum penambahan, dengan pengelompokan tanda kurung).

  • Simbol -akan selalu mewakili negasi, tidak pernah mengurangi. Jika diinginkan, Anda dapat menggantinya -dengan _atau~ untuk kemudahan I / O.
  • Parenthesis dapat disarangkan hingga tiga kali untuk menunjukkan pengelompokan: (1+(1+(1)))
  • Surat jitu tidak akan pernah secara langsung diawali dengan negasi, dan akan selalu diikuti oleh *.
  • Kurung tidak akan didahului dengan negasi -(7), melainkan sebaliknya-1*(j*5+2)
  • Tidak akan pernah ada operasi implisit. Semua perkalian akan dinyatakan sebagai (7)*7bukan (7)7, dan j*5bukan j5.
  • Tidak ada angka nol di depan.

Keluaran

Output akan dalam bentuk X+j*Y, di mana X dan Y dapat berupa bilangan bulat apa pun. Jika bilangan bulat negatif, harus diawali dengan tanda negasi.

Batasan Tambahan

Meskipun saya tidak mengetahui bahasa apa pun dengan dukungan asli, built-in yang menangani bilangan kompleks harus dilarang. Bilangan kompleks reguler adalah permainan yang adil.

Uji Kasus

Mirip dengan contoh di atas, tetapi dirapikan. Input pada satu baris dan outputkan baris di bawahnya.

(2+j*3)+(4+j*7)
6+j*10

(2+j*3)*(4+j*7)
29+j*26

(-5+j*1+j*2+2)*(4+j*7)
9+j*-9

(1+j*-1)*(1+j*1)
0+j*0 // this is why division does not exist.

j*((j*-1)+2)
-1+j*2

(2+(5+-1*(j*1))+2)
9+j*-1
PhiNotPi
sumber

Jawaban:

13

Python 2, 62 byte

def f(s):b,a=[eval(s)/2.for j in-1,1];print'%d+j*%d'%(a+b,a-b)

Kami hanya mengevaluasi ekspresi sdengan j=1dan j=-1, dan menghasilkan setengah jumlah mereka dan setengah perbedaan mereka sebagai koefisien 1dan j.

Ini bekerja karena keduanya j=1dan j=-1memenuhi persamaan mendefinisikan persamaan mendefinisikan j*j==1. Jadi, ekspresi asli dan yang disederhanakan harus sama untuk kedua nilai ini. Ekspresi yang disederhanakan adalah linear, jadi ini memberikan dua persamaan linear dalam dua yang tidak diketahui:

x + 1*y  = s(1)  = 2*a
x - 1*y  = s(-1) = 2*b

yang diselesaikan oleh x=a+b, y=a-b.

Tidak
sumber
Bahasa dengan operasi matriks juga dapat mengevaluasi ekspresi dengan j=[0 1; 1 0]dan membacakan koefisien dari baris atas.
xnor
2

Python 2, 258

class c(complex):__mul__=lambda s,o:c(s.real*o.real+s.imag*o.imag,s.real*o.imag+s.imag*o.real);__add__=lambda s,o:c(sum(map(complex,[s,o])))
import re
r=eval(re.sub("j","c(0,1)",re.sub(r"(-?\d+)",r"c(\1)",raw_input())))
print`int(r.real)`+"+j*"+`int(r.imag)`

Ini mungkin bukan pendekatan terbaik, tetapi ini adalah pertama kalinya OOP tampak seperti ide yang lumayan dalam Python untuk kode golf, jadi mengapa tidak?

Membuat kelas cyang mewarisi dari kompleks tetapi memiliki muloperasi yang berbeda . The addoperasi juga berubah sehingga mengembalikan sebuah objek dari tipe cdan tidak complex, perilaku ini diperlukan untuk mencegah kasus (a + b) * (c + d)melakukan perkalian kompleks bukan jenis khusus ini.

String input kemudian dikonversi menjadi string yang dapat dievaluasi secara alami dengan python. Ini dilakukan dengan mengubah setiap angka menjadi c(number)dan kemudian setiap jmenjadi c(0,1).

Cobalah secara online atau jalankan Test Suite

FryAmTheEggman
sumber
1

GAP , 38 byte

j:=X(Integers,"j");f:=t->t mod(j^2-1);

Pertama jdidefinisikan sebagai tak tentu, sehingga kita dapat membuat polinomial dalam j. Untuk mendapatkan nomor membingungkan yang sesuai, kami mengurangi (yaitu, mengambil sisa pembagian polinomial) dengan j^2-1. Ini memberikan istilah linear (atau konstan), dan kita dapat mengandalkan kemampuan GAP untuk menghasilkan polinomial.

Contoh:

gap> f((2+j*3)+(4+j*7));
10*j+6
gap> f((1+j*-1)*(1+j*1));
0

Peringatan: 1. Ini tidak mengambil string sebagai input, tetapi istilah nyata dalam bahasa GAP. Untuk memperbaikinya, saya bisa menggunakan EvalString. 2. Outputnya bagus dan jelas, tetapi tidak persis seperti yang ditentukan: Pesanan diubah, dan nol yang tidak perlu ditekan. Saya pikir dan berharap ini masih dalam semangat tantangan, kalau tidak saya rasa saya akan lebih baik menggunakan pendekatan matriks @ xnor.

Sievers Kristen
sumber
1
Mathematica PolynomialMod[#,j^2-1]&memiliki sifat serupa. Memang, jika kita tidak pernah mengalikan lebih dari dua angka yang membingungkan secara bersamaan (seperti halnya kasus uji tidak), maka Expand@#/.j^2->1cukuplah.
Greg Martin
Demikian pula t->t%(j^2-1)di Pari / GP.
alephalpha
1

Aksioma, 20 42 byte

f(x,n)==x^(n rem 2);m:=rule('j^n==f('j,n))

solusi sebelumnya memiliki masalah jika n<0dalam j^n tetapi ini tampaknya lebih solid, dan menyarankan dengan baik di mana ada sesuatu yang salah, bahkan jika kesempurnaan akan kembali misalnya j ^ 1.2 atau j ^ sqrt (-1) ekspresi yang sama tidak dievaluasi

(9) -> f(x,n)==x^(n rem 2);m:=rule('j^n==f('j,n))
         n
   (9)  j  == 'f(j,n)
                    Type: RewriteRule(Integer,Integer,Expression Integer)
(10) -> [m((2+j*3)+(4+j*7)), m((2+j*3)*(4+j*7)), m((-5+j*1+j*2+2)*(4+j*7))]
   (10)  [10j + 6,26j + 29,- 9j + 9]
                                            Type: List Expression Integer
(11) -> [m((1+j*-1)*(1+j*1)), m(j*((j*-1)+2)), m(2+(5+-1*(j*1))+2)]
   (11)  [0,2j - 1,- j + 9]
                                            Type: List Expression Integer
(12) -> [m(j*j*j*j),m(j*j*j),m(j^200)]
   (12)  [1,j,1]
                                            Type: List Expression Integer
(13) -> [m(j^0),m(j^-1),m(j^-2), m(j^-3)]
            1   1
   (13)  [1,-,1,-]
            j   j
                                            Type: List Expression Integer
(14) -> m(j^(3.4))
   There are no library operations named m
      Use HyperDoc Browse or issue

jika saya tidak mengikuti beberapa hukum pertanyaan: katakan padaku itu dan saya tambahkan "tidak kompetitif". Maksud saya sebagai salah satu aksioma untuk menyederhanakan formula

RosLuP
sumber
0

Batch, 52 byte

@set/aj=1,a=%1,j=-1,a-=b=(a-(%1))/2
@echo %a%+j*%b%

Setelah melihat nominasi jawaban luar biasa @ xnor, saya merasa terdorong untuk memasukkannya.

Neil
sumber