Khu vực được bao quanh bởi vòng lặp chu vi


14

Tìm diện tích của một vùng của các ô đơn vị được cho trong vòng chu vi của nó là một chuỗi các góc quay 90 độ.

Ví dụ: lấy vùng ba ô

XX
X

chúng ta vẽ vòng chu vi

L<S<L
v   ^
S R>L
v ^
L>L

Mỗi lượt được đánh dấu là trái (L), thẳng (S) hoặc phải (R). Bắt đầu từ R, lần lượt là RLLSLSLL. Vì vậy, cho đầu vào RLLSLSLL, chúng ta nên đầu ra 3 cho khu vực.

Trình tự đầu vào được đảm bảo để tìm ra một vòng lặp bao quanh một vùng duy nhất bên trái.

  • Đường dẫn kết thúc trở lại tại điểm bắt đầu, đối mặt với hướng ban đầu, tạo thành một vòng lặp.
  • Các vòng lặp không vượt qua hoặc chạm vào chính nó.
  • Vòng lặp đi ngược chiều kim đồng hồ quanh một vùng.

Tôi / O

Bạn có thể lấy đầu vào dưới dạng danh sách hoặc chuỗi ký tự LSRhoặc làm số -1, 0, 1cho trái, thẳng, phải. Đầu ra là một số nguyên dương. Phao là OK.

Các trường hợp thử nghiệm

Các đầu vào được đưa ra trong cả hai định dạng theo sau là đầu ra tương ứng của chúng.

RLLSLSLL
LLLL
SLLSLL
LSRRSLLSSLSSLSSL
SSSSSLSSSSSLSSSSSLSSSSSL

[1, -1, -1, 0, -1, 0, -1, -1]
[-1, -1, -1, -1]
[0, -1, -1, 0, -1, -1]
[-1, 0, 1, 1, 0, -1, -1, 0, 0, -1, 0, 0, -1, 0, 0, -1]
[0, 0, 0, 0, 0, -1, 0, 0, 0, 0, 0, -1, 0, 0, 0, 0, 0, -1, 0, 0, 0, 0, 0, -1]

3
1
2
7
36

Câu trả lời:


10

Brain-Flak , 112 byte

(([]){[{}]<{({}()){{}<>([{}]<([{}])>)(<>)}<>(({}[({})])[({}{})])<>}{}<>>({}<({}())>)<>([])}{})({()<({}()())>}{})

Hãy thử trực tuyến!

Chương trình này sử dụng định lý Green để tính diện tích

Vị trí hiện tại được lưu trữ trên ngăn xếp bên phải, trong một định dạng phụ thuộc vào hướng phải đối mặt.

Direction  top  second
north       -x       y
west        -y      -x
south        x      -y
east         y       x

Trong mọi trường hợp, giá trị thứ hai trên ngăn xếp sẽ tăng thêm 1 và tích phân dòng cho khu vực giảm một nửa giá trị trên đỉnh của ngăn xếp. Để bù lại, phần cuối của chương trình chia tổng số chạy cho -2.

# For each number in input
(([]){[{}]

  # Evaluate turn-handling to zero
  <

    # If turn:
    {

      # If right turn:
      ({}()){{}

        # Negate both values on other stack (reverse direction)
        <>([{}]<([{}])>)

      (<>)}

      # Swap the two stack elements and negate the new top of stack
      # This performs a left turn.
      <>(({}[({})])[({}{})])<>

    }{}

  <>>

  # Evaluate as top of stack and...
  ({}<

    # increment the number below it
    ({}())

  >)<>

([])}{})

# Divide total by -2
({()<({}()())>}{})

7

APL (Dyalog Classic) , 30 28 19 byte

-2 cảm ơn @ Adám

(+/9∘○×11○+\)0j1*+\

Hãy thử trực tuyến!

sử dụng các thủ thuật với số phức để tính tọa độ

diện tích là (x i -x i + 1 ) (y i + y i + 1 ) hoặc tương đương (x i -x i + 1 ) y i vì các đường chỉ nằm ngang hoặc dọc


Lưu vào bằng cách chuyển đổi sang cơ thể tradfn.
Adám

@ Adám đúng, tôi đã hy vọng cho một chuyến tàu và bằng cách nào đó đã quên làm điều đó ...
ngn

@ Adám ah! Tôi tìm thấy tàu :)
ngn

6

JavaScript (ES6), 52 50 byte

Đã lưu 2 byte nhờ @Neil

Mong đợi định dạng đầu vào thứ hai.

a=>a.map(k=>r+=(2-(a=a+k&3))%2*(y+=~-a%2),r=y=0)|r

Hãy thử trực tuyến!

Làm sao?

Mô tả này áp dụng cho phiên bản trước : xy đã được đảo ngược.

Điều này dựa trên công thức đã được đề cập bởi @ngn : A = (x i - x i + 1 ) y i , cũng có thể được viết là Σdx i y i trong đó dx i là -1, 0 hoặc 1.

Chúng tôi bắt đầu với r = y = 0 .

Chúng tôi theo dõi hướng hiện tại trong một :

          | a = 0 | a = 1 | a = 2 | a = 3
----------+-------+-------+-------+-------
direction | East  | South | West  | North
       dx |  +1   |   0   |  -1   |   0     <--  -(~-a % 2)
       dy |   0   |  +1   |   0   |  -1     <--  (2 - a) % 2

Nó được cập nhật với a = a + k & 3, trong đó k là phần tử hiện tại của mảng đầu vào.

Bởi vì một ban đầu chứa các mảng đầu vào, a + k được ép buộc để NaN trên phiên đầu tiên và sau đó đến 0 khi phép toán AND được áp dụng. Điều này có nghĩa là thay đổi hướng đầu tiên thực sự bị bỏ qua và chúng tôi luôn bắt đầu hướng về phía Đông. Nó không quan trọng bởi vì khu vực vẫn giữ nguyên, bất kể định hướng của hình dạng cuối cùng.

Sau đó, chúng tôi cập nhật y với y += (2 - a) % 2.

Cuối cùng, chúng tôi tính -dx với ~-a % 2và trừ y * -dx khỏi r , trong đó - ở cuối quá trình - là kết quả cuối cùng của chúng tôi.


1
a=>a.map(k=>r+=(2-(a=a+k&3))%2*(y+=~-a%2),r=y=0)|rtiết kiệm 2 byte.
Neil


3

Haskell , 71 70 69 byte

a 0 0
a x d(t:r)|k<-t+d=x*g k+a(x+g(k-1))k r
a _ _ _=0
g a=sin$a*pi/2

Giải thích: Định lý Green đưa ra công thức cho diện tích: A = ½∑ (x k + 1 + x k ) (y k + 1 -y k ), đơn giản hóa thành A = ½∑ x = 0 2x k y + Δy = 0 (x k + 1 + x k ) * 0 = ∑xΔy khi các góc quay 90 độ dọc theo trục. Chúng tôi có mã giả sau đây cho chức năng quay vòng đệ quy theo dõi vị trí và hướng x:

A x dir (turn:turns) = ΔA + A (xx) (dir+turn) turns

trong đó hướng mới, A và Δx có thể được nhìn thấy từ các bảng sau. Chúng ta có thể thấy một chu kỳ hình sin có chiều dài bốn ở cả A và Δx dọc theo trục chéo dir+turn, được thực hiện bằng cách sử dụng sinthay vì số học mô-đun.

  ↔|L S R ΔA| L  S  R  Δx| L  S  R 
         -x  0  x      0 -1  0  
          0  x  0     -1  0  1
          x  0 -x      0  1  0
          0 -x  0      1  0 -1

Hãy thử trực tuyến!



2

Thạch , 15 11 byte

Cảm ơn @xnor đã chỉ ra một bước vô dụng, tiết kiệm 2 byte
Cảm ơn @dylnan vì đã lưu một byte khác

Mong đợi định dạng đầu vào thứ hai. Trả lại một float.

+\ı*Ḟ_\×ƊĊS

Hãy thử trực tuyến! hoặc chạy tất cả các trường hợp thử nghiệm

Đã bình luận

+\ı*Ḟ_\×ƊĊS  - main link, taking the input list   e.g. [1, -1, -1, 0, -1, 0, -1, -1]
+\           - cumulative sum                     -->  [1, 0, -1, -1, -2, -2, -3, -4]
  ı*         - compute 1j ** d,                   -->  [(0+1j), (1+0j), (0-1j), (0-1j),
               which gives a list of (-dy + dx*j)       (-1+0j), (-1+0j), (0+1j), (1+0j)]
         Ċ   - isolate the imaginary part (dx)    -->  [1, 0, -1, -1, 0, 0, 1, 0] (floats)
        Ɗ    - invoke the last 3 links as a monad
    Ḟ        - isolate the real part (-dy)        -->  [0, 1, 0, 0, -1, -1, 0, 1] (floats)
     _\      - negated cumulative sum (gives y)   -->  [0, -1, -1, -1, 0, 1, 1, 0]
       ×     - compute dx * y                     -->  [0, 0, 1, 1, 0, 0, 1, 0]
          S  - sum                                -->  3

Là chỉ giữ ít nhất 2 bit đáng kể?
xnor

+\ı*Ḟ_\×ƊĊSlưu một byte
dylnan

@xnor và dylnan Cảm ơn bạn đã giúp tôi chơi bài này. Và thêm cảm ơn xnor cho tiền thưởng!
Arnauld



0

Bình thường , 14 byte

_smec^.j)sd2.:

Bộ kiểm tra

_smec^.j)sd2.:
              Q     implicit input
            .:      take all non-empty contiguous sublists
  m                map this operation onto each one:
   ec^.j)sd2
         s           the sum of the sublist
     ^.j)            raise it to the complex unit 1j to that power
    c      2         halve it
   e                take the imaginary part
_s                take the negated sum of the result

Điều này biểu thị khu vực dưới dạng tổng của -1/2 * g(sum(l))tất cả các danh sách con liền kề ltrên đầu vào, nơi glập chỉ mục mô-đun vào [0,1,0,-1]. Mã thực hiện gnhư g(x)=imag(1j**x). Có thể có một phương pháp ngắn hơn với lập chỉ mục mô-đun trực tiếp, sử dụng sinhoặc hàm số học trên x%4.

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.