สร้างจุดสุ่มนอกสี่เหลี่ยมที่กำหนดภายในแผนที่


15

บทนำ

รับภาพนี้ของสนามเด็กเล่น:

(0,0)
+----------------------+(map_width, 0)
|           A          |
|-----+-----------+----|
|  D  |     W     | B  |
|-----+-----------+----|
|           C          |
+----------------------+(map_width, map_height)
(0, map_height)

แผนที่ทั้งหมดที่เล่นในเกมนั้นคือสี่เหลี่ยมที่มีพิกัดมุม (0,0) และ (map_width, map_height) คะแนนที่มีสิทธิ์ในการวางไข่ศัตรูคือสหภาพ

S=(A,B,,D)

ความท้าทาย

เขียนโค้ดที่ส่งกลับจุดสุ่ม (x, y) ที่รับประกันว่าจะอยู่ในเอสโค้ดของคุณไม่สามารถแนะนำอคติเพิ่มเติมใด ๆ ซึ่งหมายความว่าความน่าจะเป็นของแต่ละพิกัดจะกระจายอย่างสม่ำเสมอเนื่องจากสมมติฐานที่คุณเลือกในการสร้างแบบสุ่ม | library | dev / urandom) ไม่มีอคติ

โซลูชั่นที่สั้นที่สุดในหน่วยไบต์ชนะ!

อินพุต

คุณจะได้รับจำนวน 6 map_width, map_height, W_top_left_x, W_top_left_y, W_width, W_heightตัวแปรจำนวนเต็มบวกในการสั่งซื้อ: คุณสามารถสมมติได้ว่า (คำนวณ) พื้นที่ผิวของทุกพื้นที่ (A, B, C, D, W) คือแต่ละ> 10 ดังนั้นจึงไม่มีช่องว่าง / ภูมิภาค

อินพุตตัวอย่าง: 1000, 1000, 100, 100, 600, 400

อินพุต Te ต้องมีค่า 6 ค่าที่อธิบายไว้ข้างต้น แต่สามารถส่งผ่านเป็นจำนวนอาร์กิวเมนต์น้อยลงและในลำดับใด ๆ เช่นการส่งผ่าน(map_width, map_height)เป็น puple tuple ได้รับอนุญาต สิ่งที่ไม่ได้รับอนุญาตของหลักสูตรคือพารามิเตอร์ที่คำนวณได้เช่นจุดล่างขวาของ W

เอาท์พุต

2 จำนวนเต็มสร้างแบบสุ่ม (x, y) ที่ไหน

(0x<map_width)¬(W_top_left_xx<W_top_left_x+view_width)

หรือ

(0Y<map_height)¬(W_top_left_yY<W_top_left_y+view_height)

ความหมายอย่างน้อยหนึ่งในการแสดงออกเชิงตรรกะข้างต้นจะต้องเป็นจริง

ตัวอย่าง

Input                                    Output(valid random samples)

1000 1000 100 100 600 400                10 10
1000 1000 100 100 600 400                800 550
1000 1000 100 100 600 400                800 10
1000 1000 100 100 600 400                10 550

สำหรับรายละเอียดและข้อ จำกัด สำหรับอินพุต / เอาต์พุตโปรดอ้างอิงกฎอินพุต / เอาต์พุตเริ่มต้น


ฉันคิดว่าคุณควรระบุอย่างชัดเจนว่าพิกัดเอาต์พุตเป็นจำนวนเต็ม (ซึ่งฉันถือว่าเป็นความตั้งใจโดยปริยายของคุณ)
ตลอดไป


1
@ ถึงทุกอย่างที่ระบุในส่วน "เอาท์พุท" 2 randomly generated integers (x, y)
Giuseppe

1
ขอให้เรารับอินพุตในลำดับที่แตกต่างกัน
attinat

@agto ไม่ว่าใช่เอาต์พุตจะต้องเป็นจำนวนเต็มตามที่ระบุไว้ในส่วน "เอาท์พุท"
jaaq

คำตอบ:


7

Python 2 , 114 106 102 101 ไบต์

lambda w,h,X,Y,W,H:choice([(i%w,i/w)for i in range(w*h)if(W>i%w-X>-1<i/w-Y<H)<1])
from random import*

ลองออนไลน์!


ฉันไม่แน่ใจ แต่ฉันคิดว่าควรเป็น[i%w, i/w] เพราะช่วงw*h/w=hแต่ x เชื่อมโยงกับความกว้างในตัวอย่างนี้ไม่ใช่ความสูง
jaaq

@jaaq ใช่คุณพูดถูก แก้ไขแล้วตอนนี้ขอบคุณ :)
TFeld

ฉันเพิ่งตรวจสอบเนื้อหาของรายการที่คุณสร้างและดูเหมือนว่าโซลูชันของคุณไม่ถูกต้อง การพล็อตจุดแสดงให้เห็นว่าค่าทั้งหมดอยู่ในแนวเดียวกันและไม่ได้กรอกข้อมูลทั้งภูมิภาคของ S ตามที่ตั้งใจไว้ นอกจากนี้รายการที่คุณสร้างมีค่าที่ไม่ใช่จำนวนเต็ม
jaaq

@jaaq ฉันไม่แน่ใจว่าคุณหมายถึงอะไร? พิกัดเป็นจำนวนเต็มเสมอไม่ใช่เส้น ( เช่น )
TFeld

1
@jaaq ใน Python 2 a/bเป็นการแบ่งชั้นแล้วaและถ้าbเป็นจำนวนเต็ม (ซึ่งอยู่ที่นี่)
TFeld


4

05AB1E , 23 21 20 18 17 ไบต์

L`â<ʒ²³+‹y²@«P≠}Ω

[map_width, map_height], [W_top_left_x, W_top_left_y], [W_width, W_height]การป้อนข้อมูลที่อยู่ในรูปแบบ

ขอบคุณ@Grimyสำหรับ -1 ไบต์และทำให้ฉันรู้ว่าฉันได้แนะนำข้อผิดพลาดหลังจากแก้ไขล่าสุดของฉัน

ลองมันออนไลน์ , การส่งออก 10 เอาท์พุทที่เป็นไปได้ในเวลาเดียวกันหรือตรวจสอบพิกัดเป็นไปได้ทั้งหมด (หมายเหตุเล็กน้อย: ฉันได้ลดตัวอย่างอินพุตโดยปัจจัย 10 เนื่องจากตัวกรองและตัวเลือกแบบสุ่มในตัวค่อนข้างช้าสำหรับรายการใหญ่)

คำอธิบาย:

อินพุตmap_width, map_height, [W_top_left_x, W_top_left_y], [W_width, W_height]จะเรียกว่า[Wm, Hm], [x, y], [w, h]ด้านล่าง:

L          # Convert the values of the first (implicit) input to an inner list in
           # the range [1, n]: [[1,2,3,...,Wm],[1,2,3,....,Hm]]
 `         # Push both inner lists separated to the stack
  â        # Get the cartesian product of both lists, creating each possible pair
   <       # Decrease each pair by 1 to make it 0-based
           # (We now have: [[0,0],[0,1],[0,2],...,[Wm,Hm-2],[Wm,Hm-1],[Wm,Hm]])
    ʒ      # Filter this list of coordinates [Xr, Yr] by:
     ²³+   #  Add the next two inputs together: [x+w, y+h]
          #  Check for both that they're lower than the coordinate: [Xr<x+w, Yr<y+h]
     y     #  Push the coordinate again: [Xr, Yr]
      ²    #  Push the second input again: [x, y]
       @   #  Check for both that the coordinate is larger than or equal to this given 
           #  input: [Xr>=x, Yr>=y] (the w,h in the input are ignored)
     «     #  Merge it with the checks we did earlier: [Xr<x+w, Yr<y+h, Xr>=x, Yr>=y]
      P   #  And check if any of the four is falsey (by taking the product and !=1,
           #  or alternatively `ß_`: minimum == 0)
         # After the filter: pick a random coordinate
           # (which is output implicitly as result)

1
ขอบคุณสำหรับการเพิ่มส่วนการตรวจสอบ :) ทางออกที่ดี!
jaaq

1
@jaaq ขอบคุณ! ฉันใช้ตรวจสอบตัวเองหลังจากที่รุ่นแรกของฉันซึ่งเป็นตอนที่ผมสังเกตเห็นข้อผิดพลาดที่ผมต้องแก้ไขเพราะมันถูกรวมทั้งการประสานงานเป็นผลผลิตสุ่มได้โดยไม่ต้อง[map_height, 0] ¨:)
Kevin Cruijssen

*ݨ¹‰อาจจะโดยการใช้ทั้งสองปัจจัยการผลิตครั้งแรกในฐานะL`â< [map_height, map_width]นอกจากนี้ยังIIอาจจะŠเว้นแต่ฉันพลาดอะไรบางอย่าง
Grimmy

L`â<ขอบคุณสำหรับ @Grimy สำหรับII+การŠ+คุณแน่นอนขวาว่ามันจะเหมือนกัน .. แต่น่าเสียดายที่ฉันทำข้อผิดพลาดตัวเองและมันควรจะได้รับ²³+แทนII+เพราะมันจะใช้การป้อนข้อมูลที่สามสำหรับทั้งสองI(เช่นเดียวกับที่มันจะใช้เวลาสองครั้ง อินพุตที่สามด้วยŠ) หลังจากการวนซ้ำครั้งแรกของตัวกรอง .. ดังนั้นโดยปริยายขอบคุณที่ทำให้ฉันรู้ว่าฉันมีข้อผิดพลาด :)
Kevin Cruijssen


3

PowerShell , 85 73 ไบต์

-12 ไบต์ต้องขอบคุณเขาวงกต

param($a,$b,$x,$y,$w,$h)$a,$b|%{0..--$x+($x+$w+2)..$_|random
$x,$w=$y,$h}

ลองออนไลน์!

คำตอบง่ายๆที่ดีซึ่งหินกันอาร์เรย์ที่ทำจากช่วงของค่าสำหรับแต่ละมิติและจากนั้นก็หยิบหนึ่งสุ่มและx yการบริหารจัดการเพื่อนำมาใช้มากที่สุดของรหัสโดยการประมวลผลครั้งแรกxแล้วเขียนทับ$xด้วย$yและทำงานอีกครั้ง


1
คุณสามารถบันทึกได้ไม่กี่ไบต์ลองออนไลน์!
mazzy

1
@ mazzy จริง ๆ แล้วฉันได้สะดุดในช่วงการเพิ่มประสิทธิภาพ แต่ใช้มันไปข้างหลังประหยัด 0 ไบต์
Veskah


1

เยลลี่ 11 ไบต์

p/’$€+2¦ḟ/X

ลองออนไลน์!

การเชื่อมโยง dyadic ว่าจะใช้เวลาสองมีปากเสียง[map_width, map_height], [W_width, W_height]และW_left, W_topและส่งกลับจุดสุ่มเลือกประชุมความต้องการ

คำอธิบาย

   $€       | For each of member of the left argument, do the following as a monad:
p/          | - Reduce using Cartesian product (will generate [1,1],[1,2],... up to the width and height of each of the rectangles)
  ’         | - Decrease by 1 (because we want zero-indexing)
     +2¦    | Add the right argument to the second element of the resulting list
        ḟ/  | Reduce by filtering members of the second list from the first
          X | Select a random element

1

Python 2 , 100 ไบต์

อินพุตควรอยู่ในรูปแบบของ ((map_width, W_top_left_x, W_width),(map_height, W_top_left_y, W_height))

เอาท์พุทจะได้รับในรูปแบบ: [[x],[y]]

lambda C:[c(s(r(i[0]))-s(r(i[1],i[1]+i[2])),1)for i in C]
from random import*;c=sample;r=range;s=set

ลองออนไลน์!

เอาต์พุตสุ่มที่ได้จากอินพุตตัวอย่าง:

[[72], [940]]
[[45], [591]]
[[59], [795]]
[[860], [856]]
[[830], [770]]
[[829], [790]]
[[995], [922]]
[[23], [943]]
[[761], [874]]
[[816], [923]]

1

Java (OpenJDK 8) , 100 ไบต์

W->H->r->{int x=0,y=0;for(;r.contains(x+=W*Math.random(),y+=H*Math.random());x=y=0);return x+","+y;}

ลองออนไลน์!

ใช้java.awt.Rectangleเป็นผู้ถือพารามิเตอร์บางตัว ธรรมชาติการใช้งานเหล่านั้นintฟิลด์และไม่ได้หรือfloatdouble


1
โอ้วิธีที่ดีในการท้าทายกับRectangle#containsตัวบิวอิน! : D
Kevin Cruijssen


0

ถ่าน , 55 43 ไบต์

NθNηFE²N⊞υ⟦ιN⟧I‽ΦE×θη⟦﹪ιθ÷ιθ⟧⊙υ∨‹§ιμ§λ⁰¬‹§ιμΣλ

ลองออนไลน์! การเชื่อมโยงคือการใช้รหัสเวอร์ชันอย่างละเอียด คำอธิบาย:

NθNη

ป้อนขนาดแผนที่ (ถ้าเป็นครั้งสุดท้ายฉันสามารถป้อนความสูงแบบอินไลน์เพื่อประหยัด 1 ไบต์)

FE²N⊞υ⟦ιN⟧

ป้อนสี่เหลี่ยมด้านใน (ถ้าฉันสามารถป้อนตามลำดับได้left, width, top, heightฉันสามารถใช้F²⊞υE²Nเพื่อประหยัดแบบ 3 ไบต์)

E×θη⟦﹪ιθ÷ιθ⟧

สร้างรายการพิกัดทั้งหมดในฟิลด์

Φ...⊙υ∨‹§ιμ§λ⁰¬‹§ιμΣλ

กรองรายการที่พิกัดทั้งสองอยู่ภายในสี่เหลี่ยมผืนผ้า

I‽...

พิมพ์องค์ประกอบแบบสุ่มขององค์ประกอบที่เหลือ



0

สกาล่า , 172 ไบต์

Randomness? Gotcha

(a:Int,b:Int,c:Int,d:Int,e:Int,f:Int)=>{var r=new scala.util.Random
var z=(0,0)
do{z=(r.nextInt(a),r.nextInt(b))}while((c to e+c contains z._1)|(d to e+d contains z._2))
z}

การใช้งานที่สนุกฉันคิดได้
มันทำงานอย่างไร : สร้างคู่สุ่มในแผนที่ หากอยู่ในสี่เหลี่ยมผืนผ้าด้านในให้ลองอีกครั้ง
ลองออนไลน์!


0

J , 54 47 45 39 ไบต์

(0?@{[)^:((-1&{)~(<*/@,0<:[)2{[)^:_{~&1

ลองออนไลน์!

ใช้อินพุตเป็นตาราง 3 x 2 เช่น:

grid_height  grid_width
inner_top    inner_left
inner_height inner_width
  • เลือกจุดสุ่มบนกริดทั้งหมด: 0?@{[
  • เลื่อนไปทางซ้ายและลงตามจุดบนซ้ายของสี่เหลี่ยมผืนผ้าภายใน: (-1&{)~
  • กลับไปที่ขั้นตอนที่ 1 หากจุดที่เลือกอยู่ภายใน (<*/@,0<:[)2{[คล้ายขยับสี่เหลี่ยมผืนผ้าภายใน มิฉะนั้นส่งคืนจุดสุ่มต้นฉบับที่ไม่เปลี่ยน
  • เริ่มกระบวนการทั้งหมดด้วยจุดที่เรารู้ว่าไม่ถูกต้องกล่าวคือจุดซ้ายบนของสี่เหลี่ยมภายในกำหนดโดยองค์ประกอบที่ 2 และ 3 ของรายการอินพุต: {~&1

วิธีการอื่น 45 ไบต์

{.#:i.@{.(?@#{])@-.&,([:<@;&i./{:){1&{|.i.@{.

ลองออนไลน์!

อันนี้ง่ายกว่าที่คิดและไม่ต้องห่วงกับการวนซ้ำ แต่เราสร้างเมทริกซ์ของตัวเลขทั้งหมด 0 ถึง (wxh) เปลี่ยนจากจุดเริ่มต้นด้านในคว้าเฉพาะจุดใน (0, 0) ถึง (subw, innner h) subgrid ลบออกจากภาพรวม กริดหลังจากปรับทั้งสองอย่างให้เลือกหนึ่งโดยการสุ่มจากส่วนที่เหลือและแปลงจำนวนเต็มกลับเป็นจุดโดยใช้ divmod<.@% , |~

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