มันเป็นวันฮาโลวีนอีกครั้ง!


10

คำอธิบายปัญหา

เราทุกคนรัก Twix (เพราะมันเป็นขนมที่ดีที่สุด) แต่นี่เป็นฮาโลวีนแรกของเด็ก ๆ - เราต้องคว้าลูกอมอย่างน้อยหนึ่งชนิดสำหรับพวกเขา ทุกฮัลโลวีนทุกคนที่อาศัยอยู่ในอเวนิวของ Numberline จะส่งอีเมลแจ้งว่าพวกเขาจะมอบขนมประเภทใดในปีนี้

Oh! และเราอาศัยอยู่ในโลก 1D

ด้วยความขี้เกียจเป็นพิเศษในบางวิธีและไม่ได้อยู่ในรูปแบบอื่นเราได้ทำแผนที่บ้านให้ตำแหน่งของพวกเขาไปตามถนน นอกจากนี้เรายังระบุประเภทของขนมที่พวกเขามี นี่คือแผนที่ที่เราทำในปีนี้:

 [(-2, {"Kisses", "KitKats"}),
 (1, {"KitKats", "Peanut Butter Cups"}),
 (6, {"Kisses", "Twix"}),
 (9, {"Skittles"}),
 (10, {"Twix"})]

สำหรับขาเล็ก ๆ ของเด็กเราต้องหาทางเดินที่สั้นที่สุดเริ่มต้นที่บ้านในละแวกนั้นเพื่อรวบรวมขนมอย่างน้อยหนึ่งชนิด

ตัวอย่าง

ตามคำร้องขอของผู้ใช้สองคน (รวมถึง Shaggy) ฉันจะโยนในตัวอย่างการทำงาน หวังว่านี่จะช่วยล้างสิ่งต่างๆ ใส่ :) :

 [(-2, {"Kisses", "KitKats"}),
 (1, {"KitKats", "Peanut Butter Cups"}),
 (6, {"Kisses", "Twix"}),
 (9, {"Skittles"}),
 (10, {"Twix"})]

เอาท์พุท:

[1, 2, 3]

แผนที่และทางออกอื่น ...

การป้อนข้อมูล:

[(-3, {"KitKats", "Twix"}),
(-1, {"Hundred Grands"}),
(3, {"Kisses"}),
(12, {"Hundred Grands", "Twix", "KitKats"})]

ผลผลิต :

[0, 1, 2]

เราสามารถเริ่มต้นที่ศูนย์ประสานงาน 9 แห่งเพื่อรวบรวมลูกอมไปที่บ้าน 6 และ 1 นั่นเติมโควต้าขนมโดยการเดิน 8 หน่วย แต่มันเป็นทางออกที่สั้นที่สุดหรือไม่?

กฎระเบียบ

คอมเมนต์จะต้องใช้เวลาในการโต้แย้งเดียวที่มีโครงสร้างคล้ายกับตัวอย่างและส่งออกดัชนีของบ้านเพื่อเข้าชมในการแก้ปัญหาที่สั้นที่สุด

ใช้กฎของรหัสกอล์ฟทั่วไป: วิธีแก้ไขที่สั้นที่สุดในหน่วยไบต์ชนะ!

ป.ล. นี่เป็นคำถามสัมภาษณ์ที่ฉันได้รับจาก บริษัท ด้านเทคโนโลยีรายใหญ่ที่สุดแห่งหนึ่งของโลก หากคุณไม่ชอบกอล์ฟลองค้นหาวิธีแก้ปัญหาเวลา O (k * n) โดยที่ k คือจำนวนของประเภทขนมหวานและ n คือจำนวนบ้าน

แก้ไข

ดังที่ Jonathon Allan ชี้ให้เห็นความสับสนบางอย่างเกิดขึ้นกับสิ่งที่ "ดัชนี" หมายถึงในกรณีนี้ เราต้องการที่จะส่งออกตำแหน่งบ้านในรายการอาร์กิวเมนต์และไม่ใช่พิกัดของพวกเขาในช่องทาง


6
นี่คือตัวอย่างที่จำเป็นในการทำงานและกรณีทดสอบบางอย่าง
Shaggy

2
เราสามารถรับสองข้อโต้แย้ง; รายการหมายเลขบ้านและรายการประเภทลูกกวาดที่สอดคล้องกันหรือไม่
Adám

1
@KevinCruijssen ทั้ง: ส่งออกดัชนีของบ้านเพื่อเข้าชมในการแก้ปัญหาที่สั้นที่สุด
Adám

2
ฉันสันนิษฐานว่า "ดัชนี" และ "ตำแหน่ง" มีความหมายเหมือนกัน (เช่นที่อยู่ใน Numberline Avenue น่าจะเป็นสิ่งที่เราควรส่งคืน) เป็นสิ่งที่ผิดหรือเปล่า?
Jonathan Allan

1
@KevinCruijssen คำถามยอดเยี่ยม! หมายเลขรับประกันว่าจะอยู่ในลำดับการป้อนข้อมูล และฉันจะอนุญาตให้สันนิษฐานว่าสตริงนั้นไม่มีตัวเลขเหมือนลูกอมทั้งหมดที่ฉันรู้ด้วยตัวเลขที่สะกดมันออกมา (Hundred Grands และ Three Musketeers) :)
Qfwfq

คำตอบ:


3

เยลลี่ขนาด 16 ไบต์

ŒPṪ€ẎQLƲÐṀẎISƊÞḢ

ลิงก์ monadic ยอมรับอินพุตตามที่อธิบายไว้ในรายการเรียงลำดับจากบ้านเลขที่ต่ำสุดไปสูงสุดอเวนิว (ถ้าเราจำเป็นต้องยอมรับคำสั่งใด ๆ ที่เราสามารถเติมได้) ซึ่งให้เส้นทางที่สั้นที่สุดเริ่มต้นที่บ้านเลขต่ำสุดและเดินทางขึ้นถนน

ลองออนไลน์!

หากเราต้องการค้นหาเส้นทางที่สั้นที่สุดทั้งหมดแทนที่ไบต์ต่อท้ายÞḢด้วย, ด้วยÐṂ; นี่คือ 16 ไบต์เช่นกัน

อย่างไร?

ŒPṪ€ẎQLƲÐṀẎISƊÞḢ - Link: list of [index, candies]
ŒP               - power-set
        ÐṀ       - keep those for which this is maximal:
       Ʋ         -   last four links as a monad:
  Ṫ€             -     tail €ach -- this removes the candies lists from the current list
                 -                  and yields them for use now
    Ẏ            -     tighten (to a flat list of candies offered by these hoses)
     Q           -     de-duplicate (get the distinct candies offered)
      L          -     length (how many distinct candies are on offer)
              Þ  - sort (now just the indexes of remaining sets due to Ṫ) by:
             Ɗ   -   last three links as a monad:
          Ẏ      -     tighten (to a flat list of indexes since Ṫ leaves a list behind)
           I     -     incremental differences (distances between houses)
            S    -     sum
               Ḣ - head (get the first)

1
ดี สำหรับคำอธิบายของคุณฉันคิดว่าคุณหมายถึงสูงสุดอย่างรวดเร็วสำหรับวินาทีที่สอง
Nick Kennedy

ใช่ฉันทำ
Jonathan Allan


2

05AB1E , 22 ไบต์

æʒ€θ˜I€θ˜åP}€€нD€¥OWQÏ

ถือว่าตัวเลขในรายการอินพุตถูกเรียงลำดับต่ำสุดไปสูงสุด
หากพบมากกว่าหนึ่งโซลูชันมันจะแสดงผลลัพธ์ทั้งหมด

ลองออนไลน์

คำอธิบาย:

æ            # Get the powerset (all possible combinations) of the (implicit) input-list
 ʒ           # Filter this list of combinations by:
  €θ         #  Get the last items of each (the list of strings)
    ˜        #  Flatten the list
  I          #  Get the input-list again
   €θ˜       #  Get the last items of each (the list of strings) flattened as well
      å      #  Check for each if it is in the list of strings of this combination
       P     #  Check if all are present
 }           # Close the filter (we now have all combinations, containing all unique strings)
  €€н        # Only leave the first items of each item in the combination (the integers)
     D       # Duplicate this list
      €¥     # Get the deltas (forward differences) of each
        O    # Sum these deltas
         W   # Get the lowest sum (without popping the list)
          Q  # Check for each if it's equal to this minimum
           Ï # And only leave the list of integers at the truthy indices
             # (which are output implicitly as result)


0

Haskell , 343 372 ไบต์

ขอบคุณ@ ASCII-onlyสำหรับการปรับปรุงนอกจากนี้ยังมีตัวแปร 271 ไบต์ที่เขาเสนอในความคิดเห็น :)

import Data.List
import Data.Function
f s=subsequences(map(\a@(x,y)->(x,y,[(a`elemIndices`s)!!0]))s)
g f s=if f*s<=0 then f+abs f+abs s else f+abs(f-s)
h=foldl(\(a,b,c)(d,e,f)->(g a d,nub(b++e),c++f))(0,[],[])
i s=map h(filter(not.null)s)
l m=filter(\(_,x,_)->length x==(maximum$map(\(_,x,_)->length x)m))m
m=minimumBy(compare`on`(\(p,_,_)->p))
n s=(\(_,_,l)->l)$m$l$i$f s

ลองออนไลน์!


Ungolfed

import Data.List
import Data.Function

allPaths :: [(Integer, [String])] -> [[(Integer, [String], [Int])]]
allPaths xs = subsequences(map (\a@(x,y) -> (x,y,[(a`elemIndices`s) !! 0])) s)

pathLength :: Integer -> Integer -> Integer
pathLength f s = if f*s <= 0 then f + abs f + abs s else f + abs(f - s)

traversePath :: [(Integer, [String], [Int])] -> (Integer, [String], [Int])
traversePath = foldl (\(n1, a1, c1) (n2, a2, c2) -> (pathLength n1 n2, nub (a1 ++ a2), c1 ++ c2)) (0, [], [])

allTraversedPaths :: [[(Integer, [String], [Int])]] -> [(Integer, [String], [Int])]
allTraversedPaths xs = map traversePath (filter (not . null) xs)

getCompletePaths :: [(Integer, [String], [Int])] -> [(Integer, [String], [Int])]
getCompletePaths m = filter (\(_,x,_) -> length x == ( maximum $ map (\(_,x,_) -> length x) m)) m

getFastestPath :: [(Integer, [String], [Int])] -> (Integer, [String], [Int])
getFastestPath = minimumBy (compare `on` (\(p, _, _) -> p))

getPath :: [(Integer, [String])] -> (Integer, [String], [Int])
getPath xs = (\(_,_,l) -> l) getFastestPath $ getCompletePaths $ allTraversedPaths $ allPaths xs

ความพยายามครั้งแรก


คุณควรคืนองค์ประกอบที่สามของ tuple นั้นและคุณมี newline ที่ไม่เกี่ยวข้องหลังจากการนำเข้าของคุณ
ASCII-only

315? (ยังต้องส่งคืนองค์ประกอบที่สามเท่านั้น)
เท่านั้น


ดังนั้นใช่คุณไม่สามารถ hardcode ความยาวได้
เท่านั้น


0

โซลูชันเวลา O (k * n) พร้อมพื้นที่ O (k * n)

xii0i<nxicii

i1j1i0<i1i0j0i0j0

ดังนั้นอัลกอริทึมของเราคือ:

// A[k] is the number of each candy we get from the first k houses
A := array of n bags
A[0] := {}
for k := 0 to n - 1
  A[k] := A[k - 1] + c[k - 1]
end
best_distance := ∞
best_i := -1
best_j := -1
// Find the range [i, j] such that we get all candy types
j := n
for i := n - 1 to 0
  while j > i and (A[j - 1] - A[i]) has all candy types
    j := j - 1
  end
  if (A[j] - A[i]) does not have all candy types then continue end
  distance = x[j - 1] - x[i]
  if distance < best_distance then
    best_distance = distance
    best_i = i
    best_j = j
  end
end
return best_i ..^ best_j

AO(k)O(nk)nnnO(n)O(nk)O(k)O(nk)

โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.