module mod_priority_queue
  implicit none
  type t_item
    integer :: idx, val
  end type t_item
  type t_priority_queue
    private
    integer :: num = 0
    type(t_item), pointer :: heap(:) => null()
  contains
    procedure :: offer => offer
    procedure :: clear => clear
    procedure :: poll => poll
    procedure :: peek => peek
    procedure :: size => size_of
  end type t_priority_queue
  interface t_item
    module procedure new_item
  end interface t_item
contains
  function new_item(idx,val) result(item)
    integer, intent(in) :: idx, val
    type(t_item) :: item
    item%idx = idx
    item%val = val
  end
  integer function compare(a,b)
    type(t_item), intent(in) :: a, b
    compare = -(a%val-b%val)
  end
  subroutine offer(this,item)
    class(t_priority_queue), intent(inout) :: this
    type(t_item), intent(in) :: item
    integer :: n, i
    type(t_item) :: t
    type(t_item), allocatable :: tmp(:)
    if (.not.associated(this%heap)) allocate(this%heap(1))
    if (this%num == size(this%heap)) then
      allocate(tmp(this%num))
      tmp = this%heap
      deallocate(this%heap)
      allocate(this%heap(2*this%num))
      this%heap(1:this%num) = tmp
      deallocate(tmp)
    end if
    this%num = this%num+1
    this%heap(this%num) = item
    n = this%num
    do while (n > 1)
      i = n/2
      if (compare(this%heap(n),this%heap(i)) < 0) then
        t = this%heap(n)
        this%heap(n) = this%heap(i)
        this%heap(i) = t
      end if
      n = i
    end do
  end
  subroutine clear(this)
    class(t_priority_queue), intent(inout) :: this
    if (associated(this%heap)) deallocate(this%heap)
    this%num = 0
  end
  function poll(this) result(item)
    class(t_priority_queue), intent(inout) :: this
    type(t_item) :: item, tmp
    integer :: n, i, j
    n = this%num
    item = this%heap(1)
    this%heap(1) = this%heap(n)
    this%num = this%num-1
    i = 1
    do while (2*i < n)
      j = 2*i
      if (j+1 < n .and. compare(this%heap(j+1),this%heap(j)) < 0) j = j+1
      if (compare(this%heap(j),this%heap(i)) < 0) then
        tmp = this%heap(j)
        this%heap(j) = this%heap(i)
        this%heap(i) = tmp
      end if
      i = j
    end do
  end
  function peek(this) result(item)
    class(t_priority_queue), intent(in) :: this
    type(t_item) :: item
    item = this%heap(1)
  end
  integer function size_of(this)
    class(t_priority_queue), intent(in) :: this
    size_of = this%num
  end
end module mod_priority_queue
program numbers_on_a_circle
  use mod_priority_queue
  implicit none
  type(t_priority_queue) :: pq
  type(t_item) :: item
  integer :: n, a(200000) = 0, b(200000) = 0, i, x
  integer(8) :: ans = 0_8
  read(*,*) n
  read(*,*) a(1:n)
  read(*,*) b(1:n)
  do i = 1, n
    if (b(i) < a(i)) then
      write(*,'(i0)') -1
      stop
    end if
    if (b(i) /= a(i) .and. b(i) > b(f(i-1))+b(f(i+1))) then
      call pq%offer(t_item(i,b(i)))
    end if
  end do
  do while (pq%size() > 0)
    item = pq%poll()
    i = item%idx
    x = b(f(i-1))+b(f(i+1))
    ans = ans+int((b(i)-a(i))/x,8)
    b(i) = mod(b(i)-a(i),x)+a(i)
    if (b(f(i-1)) /= a(f(i-1)) .and. b(f(i-1)) > b(i)+b(f(i-2))) then
      call pq%offer(t_item(f(i-1),b(f(i-1))))
    end if
    if (b(f(i+1)) /= a(f(i+1)) .and. b(f(i+1)) > b(i)+b(f(i+2))) then
      call pq%offer(t_item(f(i+1),b(f(i+1))))
    end if
  end do
  do i = 1, n
    if (b(i) /= a(i)) then
      write(*,'(i0)') -1
      stop
    end if
  end do
  write(*,'(i0)') ans
contains
  integer function f(i)
    integer, intent(in) :: i
    f = mod(n+i-1,n)+1
  end
end program numbers_on_a_circle

Measured memory_bytes: 3416