Você está na página 1de 5

Nama : Yolanda Hertita Pratama

NRP : 5116100052
PENJABARAN TENTANG BEBERAPA PENYELESAIAN SAYA PADA SOAL SPOJ

1. MINST
-Ada array dari N integer, kita harus membuat semua bilangan yang ada = 0, dengan cara:
-Pilihlah beberapa bilangan, berapapun, misal K.
-Dari K bilangan yang terpilih, kita bisa membagi K menjadi dua kelompok, kelompok A yaitu
kelompok yang ditambahkan 1 pada setiap langkahnya, kelompok B yaitu kelompok yang dikurangkan 1
pada setiap langkahnya.
Penyelesaian
Karena kita bisa memilih berapapun nilai K (A, B juga), maka yang kita lakukan pada setiap langkah
adalah:
-Jika bilangan(bilangan-bilangan) yang ada sama dengan 0, jangan kita pilih (jangan diutak atik), selain
itu,
-Jika bilangan itu positif maka kita masukkan pada kelompok B, agar pada setiap langkahnya kita
kurangkan sampai dia sama dengan 0
-Jika bilangan itu negatif maka kita masukkan pada kelompok A, agar pada setiap langkahnya kita
tambahkan sampai dia sama dengan 0
-Tentu saja pada kelompok A dan B jika dia sudah sama dengan 0 maka jangan pilih dia lagi (jangan
diutak atik lagi)
Maka dari itu untuk mendapatkan jawaban dari soal ini, kita hanya perlu mendapatkan nilai terbesar

dari nilai absolut dari array N integer.


Yang saya lakukan adalah array tersebut disort, lalu membandingkan nilai absolut array[0] dan array[n1].
2. FACTB12 Factorial Base 12
-Menghitung banyak angka 0 tak terputus di belakang pada n!, akan tetapi n! setelah dinyatakan dalam
base 12.
Penyelesaian
Menurut saya jika ingin menyelesaikan soal ini, kita harus paham bagaimana menyelesaikan soal
FCTRL. Ini mirip, hanya saja pada FCTRL hanya dalam base 10.
Untuk mendapatkan banyaknya angka 0 tak terputus dibelakang pada n! dalam base 10, kita hanya perlu
menghitung
n
n
n
+ 2 + 3 +
5
5
5

Itu didapatkan karena kita mendapatkan angka 0 setiap kita mengalikan 5 dengan 2, tapi jangan lupa
pada saat kelipatan 25, 5 dihitung 2 kali, dan setiap kelipatan 125, 5 dihitung 3 kali dst..
Sebenarnya kita juga perlu menghitung banyaknya faktor 2, namun pada kondisi ini dapat diabaikan
karena banyaknya sudah pasti > dari 5.
2

Lalu ide dari soal ini saya gunakan pada FACTB12. 12 memiliki faktorisasi prima yaitu 2 x 3 . Nah
jadi kita perlu menghitung banyaknya faktor 2 yang muncul dan faktor 3 yang muncul dalam n!
Banyaknya faktor 2 yang muncul = f2 =

n
n
n
+ 2 + 3 +
2
2
2

Banyaknya faktor 3 yang muncul = f3 =

n
n
n
+ 2 + 3 +
3
3
3

2
Akan tetapi karena angka 2 dihitungnya setiap ia 2 kali muncul (karena 2 x 3 )

Maka kita bandingkan nilai minimum dari (f2/2, f3) untuk mendapatkan jawaban dari soal ini.
3. LEXI2 Lexicographic Order 2
-Diberikan n-buah bilangan asli pertama (dalam urutan yang acak), carilah k-th next permutation dari
bilangan yang diberi tadi.
Penyelesaian
Pertama, kita harus mengetahui bilangan yang diberikan pada urutan lexicographic dia menempati urutan
ke berapa.
Untuk mendapatkan bilangan itu terletak pada urutan ke berapa yang kita lakukan adalah menggunakan
permutasi dalam matematika
Jadi pada awalnya kita sorting dulu (karena ini sudah pasti n-buah bilangan asli pertama, maka kita tidak
perlu menggunakan algoritma sort, buat dalam array saja, misal x)
Kalau kita mengambil bilangan terkecil untuk diletakkan didepan, maka range jawabannya pasti pada
1 (n1)!
Kalau kita mengambil bilangan terkecil kedua untuk diletakkan didepan, maka range jawabanya pasti
pada ( n1 ) !+1 2.(n1)!
Dst...
Kita set nilai sum = 1 dulu.
Jadi kita ambil angka pertama, dia terletak pada urutan ke-berapa pada array x, misal d, lalu kita
tambahkan sum dengan (d-1)*(n-i)!, dengan i merupakan banyak kotak kosong yang bisa diisi
kemungkinan.
Kita buat dengan contoh angka saja agar lebih mudah

Misal angka yang diberikan 3 4 2 1


Array x 1 2 3 4
3___
3 pada array x menempati posisi terkecil ke-3
Berarti sum += (3-1)*(3!) = 1 + 12 = 13
Array x 1 2 3 4
34__
4 pada array x sekarang menempati posisi terkecil ke-3
Maka sum += (3-1)*(2!) = 13 + 4 = 17
Array x 1 2 3 4
342_
2 pada array x sekarang menempati posisi terkecil ke-2
Maka sum += (2-1)*1! = 17 + 1 = 18
Angka dibelakang sudah pasti. Maka sum sudah tidak perlu ditambah lagi.
Nah, sudah kita dapatkan posisi angka tersebut dalam leksikografis, lalu langkah selanjutnya kita akan
menghitung kth permutation setelah bilangan tersebut.
Jika hasilnya lebih dari n!, maka kita kurangkan dengan n! agar kembali pada awal lagi.
Untuk menghitungnya, hampir sama dengan menghitung yang tadi. Kita hanya perlu mencari tahu nilai
m maksimal yang jika m-1 dikalikan (n-i)! hasilnya masih lebih kecil dari z. Misal sekarang kita ingin
mencari tahu urutan ke 22 (z).
Array x 1 2 3 4
?___
Jika m = 1 0*3! = 0, masih < dari 22
Jika m = 2 1*3! = 6, masih < dari 22
Jika m = 3 2*3! = 12, masih < dari 22
Jika m = 4 3*3! = 18, masih < dari 22
Ini maksimal, maka yang diambil adalah urutan 4 terkecil dari array x, saat ini yaitu 4
4___
z = z- 18 = 22-18 = 4
Array x 1 2 3 4
4?__
Jika m = 1 0*2! = 0, masih < dari 4
Jika m = 2 1*2! = 2, masih < dari 4
Jika m = 3 2*2! = 4, tidak < dari 4
Maka yang diambil adalah urutan 2 terkecil dari array x, saat ini yaitu 2

42__
z=z2=42=2
Array x 1 2 3 4
4 2?_
Jika m = 1 0*1! = 0, masih < dari 2
Jika m = 2 1*1! = 1, masih < dari 2
Jika m = 3 2*1! = 2, tidak < dari 2
Maka yang diambil adalah urutan 2 terkecil dari array x, saat ini yaitu 3
423_
Array x 1 2 3 4
Angka terakhir pastilah urutan ke 1, pada saat ini yaitu 1.
4231
4. BTCK
Diberikan 10 bilangan positif integers n1, n2, ..., n10 dan sebuah bilangan k,
Cari permutasi dari a1, a2, ..., a10 dari {0, 1, 2 , ... 9} dimana
a 1n1+ a2n 2++ a10n 10 k
Jika ada lebih dari 1 kemungkinan, print yang lexicografisnya paling kecil.
Jika tidak ada, print -1
Penyelesaian
Yang saya lakukan adalah menggunakan fungsi next-permutation yang saya dapatkan dari blog
https://www.nayuki.io/page/next-lexicographical-permutation-algorithm
Akan tetapi menurut saya kompleksitasnya sama dengan kompleksitas fungsi next_permutation() yang
disediakan oleh c++
Saya mencoba menggunakan inequality, yaitu Rearrangement Inequality

Jadi
saya
sort
array

tersebut, bilangan terbesar 1 dikalikan indeks terkecil 1, bilangan terbesar 2 dikalikan


indeks terkecil 2, dst.. jika hasilnya tidak lebih kecil sama dengan k, maka sudah pasti
tidak ada permutasi yang memenuhi soal, jadi langsung saja print -1.

Você também pode gostar