Bersikap hormat di kamar kecil

35

Tentu saja, jaringan SE sangat berpengetahuan tentang bagaimana menjadi terhormat di kamar kecil, tetapi bagi Anda yang membutuhkan rekap, menghormati berarti menyiram toilet, dll. Yang terpenting, meskipun, itu berarti menggunakan kios sejauh mungkin. dari orang lain sebanyak mungkin.

Tantangan

Diberikan cetak biru dari serangkaian kios dengan indikasi yang digunakan sebagai string, Anda harus kembali atau mencetak dari fungsi atau program di mana tempat paling terhormat untuk melakukan bisnis Anda adalah.

Input

 0 1 2 3 4 5    <- The stall number which is not actually visible in the input. 
| | |-| |-|-|   <- the stalls

Kios diberi nomor dalam urutan menaik dari kiri ke kanan. Akan selalu ada setidaknya satu kios kosong. Mungkin ada hingga 50 kios dalam satu input. Anda juga dapat mengambil input sebagai array atau string 0s dan 1s atau booleans jika Anda lebih suka melakukannya.

Kios-kios yang digunakan ada -di dalamnya (di antara pipa-pipa).

Hasil

Kios yang paling terhormat untuk dikunjungi adalah kios yang rata-rata terjauh dari yang sedang digunakan. Jarak antara dua kios adalah nilai absolut dari perbedaan angka di atas mereka.

Untuk memperjelas: Anda menemukan jarak rata-rata dari semua kios — bukan hanya yang berdekatan.

Anda harus menampilkan jumlah terendah dari kios paling terhormat untuk pergi ke yang kosong .

Contohnya

Input:
|-| |-| OR 101
Output:
1

Input:
| | |-| |-|-| OR 001011
Output:
0

Input:
|-| |-| | | | |-|-| OR 101000011
Output:
1

Input: 
|-| | | | | |-|-| | | | | OR 100000110000
Output:
11

Input:
|-|-|-|-| | | | | | |-| OR 11110000001
Output:
9

Input:
|-| | OR 10
Output:
1

Input:
|-| | |-| OR 1001
Output:
1

Ini adalah , jadi kode terpendek dalam byte menang!

Anda dapat menggunakan pengindeksan berbasis 0 atau 1 dalam jawaban Anda - mana yang Anda inginkan; jika Anda menggunakan 1 pengindeksan berbasis, maka Anda harus mengatakannya secara eksplisit dalam jawaban Anda.

Daniel
sumber
35
" Tentu saja, jaringan SE sangat berpengetahuan tentang bagaimana menjadi terhormat di kamar kecil " [rujukan?]
Alex A.
7
@AlexA .: Lihat pertanyaan dan jawaban toilet di travel.stackexchange untuk menilai tingkat pendidikan jaringan SE (atau untuk mendidik diri sendiri).
Jonas
30
Tetapi semua orang tahu bahwa kriteria hormat adalah memaksimalkan jarak minimum , bukan rata - rata :-)
Luis Mendo
2
@Dappapp Anda harus menambahkan [1,0,0,1]sebagai test case. Tak satu pun dari kasus uji saat ini memverifikasi apakah ikatan rusak dengan benar.
Dennis
8
Mengapa 101000011mengembalikan 1 (bukan 4 atau 5)?
Amani Kilumanga

Jawaban:

11

Jelly , 10 9 byte

JạþTS׬MḢ

Menggunakan pengindeksan berbasis 1. Cobalah online! atau verifikasi semua kasus uji .

Bagaimana itu bekerja

JạþTS׬MḢ  Main link. Argument: A (array of Booleans)

J          Yield all indices of A.
   T       Yield all truthy indices of A.
 ạþ        Compute the table of absolute differences.
    S      Compute the sums of all columns.
           For each index, this yields the sum of all distances to occupied stalls.
     ׬    Multiply each sum by the logical NOT of the corresponding Boolean in A.
           This zeroes sums that correspond to occupied stalls.
       M   Maximal; yield an array of all indices of maximal sums.
        Ḣ  Head; extract the first index.
Dennis
sumber
Saya percaya itu 9 karakter, bukan 9 byte.
René Nyffenegger
Jelly menggunakan halaman kode khusus yang mengkodekan satu-satunya karakter yang dimengerti sebagai masing-masing byte tunggal. The byte link dalam poin sundulan untuk itu.
Dennis
Saya tidak menyadari hal ini ... terima kasih telah menunjukkannya.
René Nyffenegger
@Dennis Apakah Anda membuat skrip pengguna komentar otomatis sehingga Anda cukup mengeklik "Jelly byte komentar" dan itu akan mempostingnya?
NoOneIsHere
@NoOneIsHere Saya punya itu script pengguna ( bukan milik saya ), tapi saya belum menambahkan ini. Saya mungkin harus ...
Dennis
6

Swift, 158, 157, 128, 100 Bytes

Mengambil input dari Array<Bool>variabel i, mengembalikan jawaban dari ekspresi terakhir.

let e=i.characters.map{$0>"0"}.enumerate()
e.flatMap{$1 ?nil:$0}.map{a in(a,e.flatMap{$1 ?$0:nil}.map{abs(a-$0)}.reduce(0){$0+$1})}.maxElement{$0.1 < $1.1}!.0

Edit 1:

Menyimpan byte dengan mengkonversi ke bools melalui perbandingan string

let e=i.characters.map{$0=="1"}.enumerate()
e.flatMap{$1 ?nil:$0}.map{a in(a,e.flatMap{$1 ?$0:nil}.map{abs(a-$0)}.reduce(0){$0+$1})}.maxElement{$0.1 < $1.1}!.0

Edit 2:

Mengolah ulang algoritma saya:

let e=i.characters.map{$0=="1"}.enumerate()
e.map{x in(x.0,x.1 ?0:e.reduce(0){$1.1 ?$0+abs(x.0-$1.0):$0})}.max{$0.1<$1.1}!.0

Edit 3:

Mengambil keuntungan dari aturan baru yang memungkinkan mengambil input langsung dari array boolean.

let e=i.enumerated()
e.map{x in(x.0,x.1 ?0:e.reduce(0){$1.1 ?$0+abs(x.0-$1.0):$0})}.max{$0.1<$1.1}!.0

Tidak Disatukan:

// for the sake of easier copy/pasting of input, take it as string
let s = "100000110000"

// convert input to true for taken, false for free
// this is the input the golfed version actually uses
let input = s.characters.map{$0>"0"}

// Returns an array of tuples storing the array values (vacancy of the stall) and their index (their location)
let valueIndexPairs = bools.enumerated()

// Returns an array of pairs of locations and their avg distance to others
let locationDistancePairs = valueIndexPairs.map{(valueIndexPair: (Int, Bool)) -> (Int, Int) in

    let averageDistance = valueIndexPairs.reduce(0) {partialSum, otherStall in

        let otherStallIsTaken = otherStall.1

        if otherStallIsTaken {
            //don't let other stalls effect average if they're taken
            return partialSum
        }
        else {
            let thisStallLocation = valueIndexPair.0
            let otherStallLocation = otherStall.0
            let distanceToOtherStall = abs(thisStallLocation - otherStallLocation)
            return partialSum + distanceToOtherStall 
        }       
    }

    //if this stall is taken, treat its average distance to others as 0
    let thisStallsLocation = valueIndexPair.0
    let isThisStallTaken = valueIndexPair.1
    return (thisStallsLocation, isThisStallTaken ? 0 : averageDistance)
}

//find location where average distance is maxiumum
let bestLocationIndexPair = locationDistancePairs.max{$0.1 < $1.1}!

let bestLocation = bestLocationIndexPair.0

print(bestLocation)
Alexander - Pasang kembali Monica
sumber
2
Saya suka jawaban cepat
downrep_nation
Sangat menyenangkan untuk belajar :) Meskipun cenderung menjadi bahasa yang cukup menyakitkan untuk bermain golf. Pustaka standar benar-benar minimal (Anda lebih sering menggunakan Yayasan), bahasanya dimaksudkan untuk sangat ekspresif, dan diketik secara statis. Sintaks penutupan BENAR-BENAR baik
Alexander - Reinstate Monica
Saya mungkin harus menjelaskan cara kerja kode ini lol
Alexander - Reinstate Monica
1
@downrep_nation Saya menambahkan verison ungolfed, jika Anda tertarik
Alexander - Reinstate Monica
Mungkin menyimpan 3 byte dengan menghapus "biarkan" idk jika Anda membutuhkannya atau tidak, tetapi dari apa yang saya pahami Anda tidak perlu "biarkan" yang hanya berfungsi sebagai indikator nilai konstan
Rohan Jhunjhunwala
5

Jelly , 13 byte

1-diindeks.

³Tạ⁸S
JUÇÞḟTṪ

Cobalah online!

Algoritma

Implementasi yang naif dari pertanyaan tersebut.

Biarawati Bocor
sumber
lol sekitar 16 kali lebih pendek dari jawaban saya +1! (1! == 1)
Rohan Jhunjhunwala
@RohanJhunjhunwala Apa yang kamu katakan?
Leaky Nun
Pada dasarnya Java tidak pernah dapat bersaing dengan Jelly Seeing jawaban yang panjangnya 12 byte (lebih pendek dari program java yang mungkin) adalah lucu. Jadi, dapatkan upgoat ..
Rohan Jhunjhunwala
@LeakyNun lol melewatkan golf: D
Rohan Jhunjhunwala
2
1001 menghasilkan 3 ketika harus mengembalikan 2
Daniel
5

Java "hanya" 270 200 196 187 196 138 148 146 byte!

menyelamatkan 4 13 byte yang tak terhitung jumlahnya berkat Leaky Nun! 1 byte berkat Micheal Golfed

int m(boolean[]b){int r=0,l=b.length,i,j,k=0,z=r;for(i=0;i<l;i++){if(b[i])for(j=0,k=0;j<l;j++)if(!b[j])k+=i>j?i-j:j-i;if(k>z){r=i;z=k;}}return r;}

Tidak disatukan

int m(int[] s) {
        int l=s.length,i,j=0,k=0;
    boolean[] b = new boolean[l];
    int[] a = new int[l];
    //see what stalls are open
    for (i = 0; i < s.length; i++) {
        if (s[i] == 0){
            b[i] = true;
        }
    }
    //assign the sum of distance to the a[]
    for (i = 0; i < l; i++) {
        if (b[i]) {
            for (j = 0; j < l; j++) {
                if (!b[j]) {
                    a[i]+= Math.abs(i - j);
                }
            }
        }
    }
    //find the stall the greatest distance away breaking ties based on the furthest left
    for (i = 0; i < l; i++) {
        if (b[i] && (a[i] > k || k == 0)) {
            k = a[i];
            j=i;
        }
    }
    //return the index
    return j;
}

input sebagai array boolean di mana true menyiratkan kios terbuka.

Rohan Jhunjhunwala
sumber
Komentar bukan untuk diskusi panjang; percakapan ini telah dipindahkan ke obrolan .
Alex A.
Anda tidak perlu array a.
Leaky Nun
@ LeakyNun bagaimana cara menghapusnya?
Rohan Jhunjhunwala
Dengan menemukan minimum dalam satu iterasi (gabungkan bagian luar untuk loop)
Leaky Nun
oh @LeakyNun akan lakukan ketika saya kembali hari ini
Rohan Jhunjhunwala
4

Ruby, 79 78 76 + nbendera = 77 byte

Output adalah pengindeksan berbasis 0. Input adalah garis STDIN dari 0 dan 1.

p (r=0...~/$/).max_by{|i|k=0;$_[i]>?0?0:r.map{|j|k+=$_[j]<?1?0:(j-i).abs};k}
Nilai Tinta
sumber
1
0...~/$/adalah trik yang bagus. 👍🏻
Jordan
2

MATL , 14 byte

~ftGf!-|Xs&X>)

Cobalah online!

Output berbasis 1.

Penjelasan

~f     % Implicitly take input. Compute row vector with indices of zeros
t      % Duplicate that
Gf!    % Push input again. Compute column vector of indices of ones
-|     % Absolute differences with broadcast. Gives 2D array with all combinations
Xs     % Sum of each column
&X>    % Arg max. Gives the index of the first maximizer if there are several
)      % Index into row vector of indices of zeros. Implictly display
Luis Mendo
sumber
2

Perl 84 + 3 ( -alpbendera) = 87 byte

for$i(0..$#F){$t=0;map{$t+=abs($i-$_)*$F[$_]}0..$#F;($m,$_)=($t,$i)if$m<$t&&!$F[$i]}

Perlu -alpbendera untuk dijalankan. Mengambil string 1 dan 0 dipisahkan oleh spasi sebagai input. Contohnya :

perl -alpe '$m=0;for$i(0..$#F){$t=0;map{$t+=abs($i-$_)*$F[$_]}0..$#F;($m,$_)=($t,$i)if$m<$t&&!$F[$i]}' <<< "1 0 1
0 0 1 0 1 1
1 0 1 0 0 0 0 1 1
1 0 0 0 0 0 1 1 0 0 0 0
1 1 1 1 0 0 0 0 0 0 1
1 0"

Perhatikan bahwa saya menambahkan $m=0di awal, tetapi itu hanya untuk mengujinya pada beberapa entri.

Dada
sumber
Saya menghitung +7: F'' alp. -Tidak dihitung.
NoOneIsHere
@NoOneIsHere Hum, memang, itu akan menjadi buruk bagiku. Terima kasih
Dada
2

Matlab, 87 byte

n=input('');k=numel(n);[a b]=ndgrid(1:k);[x y]=max(sum(abs(a-b).*repmat(n,k,1)').*~n);y

Mengambil array satu dan nol; menggunakan pengindeksan berbasis 1.
Seperti beberapa jawaban lain, memaksimalkan total bukan jarak rata-rata.
Mungkin masih ada lagi kemungkinan bermain golf ...

pajonk
sumber
2

JavaScript (ES6), 87 86 82 75 byte

a=>a.map((u,i)=>u||(a.map((v,j)=>u+=v*(i>j?i-j:j-i)),u>x&&(x=d,r=i)),x=0)|r

Mengambil array boolean (true / false atau 1/0). Tidak ada gunanya menghitung jarak rata-rata karena mereka semua menggunakan faktor umum yang sama, jadi hitung saja jarak total untuk setiap kios dan temukan indeks pertama dari yang tertinggi. Sunting: Disimpan 1 byte dengan menggunakan *alih-alih &&. Disimpan 5 byte dengan mencari jarak tertinggi secara manual berdasarkan komentar dari @Dendrobium. Disimpan 7 byte dengan menggunakan kembali usebagai akumulator pengurangan semu berdasarkan komentar oleh @ edc65.

Neil
sumber
79 byte:a=>(x=0,a.map((o,i)=>x<(t=a.reduce((r,u,j)=>r+(b=i-j)*b*u*!o,0))&&(x=t,r=i)),r)
Dendrobium
@Dendrobium Pertanyaannya menanyakan jarak absolut; Anda tampaknya menghitung jarak RMS.
Neil
1
Menggunakan array sebagai input - ide bagus. Menghitung total, bukan rata-rata - ide bagus. Menggunakan reducebukannya map- mmmm
edc65
75:s=>s.map((u,i)=>u||(s.map((w,j)=>u-=w*Math.abs(j-i)),u<x&&(x=u,r=i)),x=0)|r
edc65
@ Neil Tidak cukup RMS, hanya jarak kuadrat, yang seharusnya tidak mempengaruhi hasil dari solusi kecuali ada ikatan dalam total jarak input nonsimetrik (misalnya 1100011101ikatan di 2dan 8ketika menggunakan absolut, 8ketika menggunakan kuadrat), bukan karena itu penting karena tampaknya aturan telah diklarifikasi dan ikatan sekarang diselesaikan dengan kios paling kiri ...
Dendrobium
1

J, 27 byte

(#{:@-.~]/:[:+/]|@-/~#)i.@#

Penerjemah online .

Biarawati Bocor
sumber
1

Ruby, 87 76 byte

Lemparkan draf pertama ini dengan cepat, tetapi sementara itu Value Ink sudah memposting jawaban Ruby 80 byte ...

edit: melepas beberapa byte dengan bantuan dari Value Ink:

->a{(r=0...a.size).max_by{|i|a[i]?0:r.map{|j|a[j]?(i-j).abs: 0}.reduce(:+)}}

Ini adalah fungsi anonim yang mengambil array nilai true / falsy, seperti misalnya:

f=->->a{(r=0...a.size).max_by{|i|a[i]?0:r.map{|j|a[j]?(i-j).abs: 0}.reduce(:+)}}
# Test case number 5:
p f[[1, 1, 1, 1, nil, nil, nil, nil, nil, nil, 1]] # => 9
daniero
sumber
1
Menetapkan kisaran awal untuk variabel (r=0...a.size)dan kemudian peta pada bahwa alih-alih menggunakan with_index: r.map{|j|a[j]?(i-j).abs: 0}. Ini seharusnya membuat Anda 78 byte.
Value Ink
@ ValueInk Luar Biasa, terima kasih! Dengan hanya fungsi, tanpa tugas, saya mendapatkan 76 byte
daniero
1

Mathematica, 53 byte

MaximalBy[a=PositionIndex@#;a@0,Tr@Abs[#-a@1]&][[1]]&

Menggunakan pengindeksan berbasis 1 dan mengambil input sebagai daftar 0s dan 1s.

alephalpha
sumber
0

Javascript ES6 - 98 95 91 86 84 88 byte

Sunting: Tampaknya kios paling kiri harus digunakan dalam kasus dasi. Jarak kuadrat tidak lagi berfungsi, dikembalikan ke jarak absolut.

(r,x=0,f=g=>r.reduce(g,0))=>f((p,o,i)=>x<(o=f((p,c,j)=>p+c*!o*Math.abs(i-j)))?(x=o,i):p)

Tidak Disatukan:

(r,                            // string input
 x=0,                          // current max distance
 f=g=>r.reduce(g,0))=>         // iterator function
   f((p,o,i)=>                 // for each stall
     x<(o=f((p,c,j)=>          // iterate through all stalls and
       p+c*!o*Math.abs(i-j)))? //   calculate sum of distances from current stall
     (x=o,i):                  // if total dist is greater than x, update x, return index
     p)                        //   else return previous max index

Tes berjalan:

f=(r,x=0,f=g=>r.reduce(g,0))=>f((p,c,i)=>x<(c=+c?0:f((p,c,j)=>p+c*Math.abs(i-j)))?(x=c,i):p)
f([1,0,1])                   // 1
f([0,0,1,0,1,1])             // 0
f([1,0,1,0,0,0,0,1,1])       // 1
f([1,0,0,0,0,0,1,1,0,0,0,0]) // 11
f([1,1,1,1,0,0,0,0,0,0,1])   // 9
f([1,0])                     // 1
Dendrobium
sumber
0

Lua, 165 150 Byes

n=arg[1]n=n:gsub("%|%-","1"):gsub("%| ","0")i=0 for s in n:gmatch("0+")do i=(i<#s)and(#s)or(i)end n,l=n:find(("0"):rep(i))print(n+math.floor((l-n)/2))

Ini sedikit menipu menggunakan fakta bahwa secara umum, lua melewati tabel yang disebut arg yang berisi input baris perintah apa pun untuknya.

Saya agak kecewa karena saya menggunakan for in loop, tapi saya tidak bisa memikirkan cara yang lebih kecil untuk melakukannya.

Juga, Karena lua, 1 pengindeksan berbasis digunakan.

Edit Terpotong 15 byte dari gsub yang boros.

ATaco
sumber
0

C #, 127 byte

public int G(char[]s){int i=0;var l=s.ToLookup(b=>b,b=>i++);return l['0'].OrderBy(j=>l['1'].Average(p=>Math.Abs(p-j))).Last();}

Test Bed

public static void Main() {
    var respectful = new Respectful();
    foreach (var kvp in testCases) {
        $"{kvp.Key}: Expected {kvp.Value} Actual {respectful.G(kvp.Key.ToCharArray())}".Dump();
    }
}

public static readonly List<KeyValuePair<string, int>> testCases = new List<KeyValuePair<string, int>> {
    new KeyValuePair<string, int>("101", 1),
    new KeyValuePair<string, int>("001011", 0),
    new KeyValuePair<string, int>("101000011", 1),
    new KeyValuePair<string, int>("100000110000", 11),
    new KeyValuePair<string, int>("11110000001", 9),
    new KeyValuePair<string, int>("10", 1),
    new KeyValuePair<string, int>("1001", 1),
};

public class Respectful {
    public int G(char[]s){int i=0;var l=s.ToLookup(b=>b,b=>i++);return l['0'].OrderBy(j=>l['1'].Average(p=>Math.Abs(p-j))).Last();}
}
ErikE
sumber