結果

問題 No.800 四平方定理
ユーザー 👑 obakyanobakyan
提出日時 2019-06-06 22:07:32
言語 Lua
(LuaJit 2.1.1696795921)
結果
AC  
実行時間 1,962 ms / 2,000 ms
コード長 2,493 bytes
コンパイル時間 37 ms
コンパイル使用メモリ 5,120 KB
実行使用メモリ 19,328 KB
最終ジャッジ日時 2024-10-01 19:37:33
合計ジャッジ時間 21,419 ms
ジャッジサーバーID
(参考情報)
judge2 / judge1
このコードへのチャレンジ
(要ログイン)

テストケース

テストケース表示
入力 結果 実行時間
実行使用メモリ
testcase_00 AC 16 ms
5,248 KB
testcase_01 AC 19 ms
5,248 KB
testcase_02 AC 22 ms
5,248 KB
testcase_03 AC 14 ms
5,248 KB
testcase_04 AC 13 ms
5,248 KB
testcase_05 AC 14 ms
5,248 KB
testcase_06 AC 19 ms
5,248 KB
testcase_07 AC 31 ms
5,248 KB
testcase_08 AC 18 ms
5,248 KB
testcase_09 AC 20 ms
5,248 KB
testcase_10 AC 752 ms
11,136 KB
testcase_11 AC 628 ms
11,136 KB
testcase_12 AC 667 ms
11,136 KB
testcase_13 AC 859 ms
11,136 KB
testcase_14 AC 732 ms
11,136 KB
testcase_15 AC 944 ms
11,136 KB
testcase_16 AC 752 ms
11,136 KB
testcase_17 AC 710 ms
11,136 KB
testcase_18 AC 812 ms
19,328 KB
testcase_19 AC 797 ms
19,328 KB
testcase_20 AC 2 ms
5,248 KB
testcase_21 AC 1 ms
5,248 KB
testcase_22 AC 1,094 ms
19,328 KB
testcase_23 AC 1,800 ms
19,328 KB
testcase_24 AC 1,391 ms
19,328 KB
testcase_25 AC 1,962 ms
19,328 KB
testcase_26 AC 1 ms
5,248 KB
testcase_27 AC 1 ms
5,248 KB
testcase_28 AC 1,009 ms
19,328 KB
testcase_29 AC 1,214 ms
19,200 KB
testcase_30 AC 1,402 ms
19,328 KB
testcase_31 AC 973 ms
19,328 KB
testcase_32 AC 1,333 ms
19,328 KB
権限があれば一括ダウンロードができます

ソースコード

diff #

local mfl = math.floor
local mmi = math.min
local function lower_bound(ary, x, max)
  local num = #ary
  if num == 0 then return 1 end
  if(x <= ary[1]) then return 1 end
  if(ary[max] < x) then return max + 1 end
  local min = 1
  while(1 < max - min) do
    local mid = mfl((min + max) / 2)
    if(ary[mid] < x) then
      min = mid
    else
      max = mid
    end
  end
  return max
end

local n, d = io.read("*n", "*n")
local sq = {}
local same_ev, same_odd = {}, {}
local same_evlen, same_oddlen = 0, 0
for i = 1, n do
  sq[i] = i * i
  if 2 * sq[i] < d + n * n then
    if i % 2 == 0 then
      same_evlen = same_evlen + 1
      same_ev[same_evlen] = 2 * sq[i]
    else
      same_oddlen = same_oddlen + 1
      same_odd[same_oddlen] = 2 * sq[i]
    end
  end
end
local evens, odds, evod = {}, {}, {}
local evlen, odlen, eolen = 0, 0, 0
for i = 1, n - 1 do
  for j = i + 2, n, 2 do
    if d + n * n <= sq[i] + sq[j] then break end
    if i % 2 == 0 then
      evlen = evlen + 1
      evens[evlen] = sq[i] + sq[j]
    else
      odlen = odlen + 1
      odds[odlen] = sq[i] + sq[j]
    end
  end
  for j = i + 1, n, 2 do
    if d + n * n <= sq[i] + sq[j] then break end
    eolen = eolen + 1
    evod[eolen] = sq[i] + sq[j]
  end
end
table.sort(evens)
table.sort(odds)
table.sort(evod)
local cnt = 0
for w = 1, n do
  local w2d = d + sq[w]
  local curmax_odd, curmax_even, curmax_evod = odlen, evlen, eolen
  for z = 1, n do
    local tgt = w2d - sq[z]
    if tgt <= 0 then break end
    if tgt % 4 == 0 then
      local a = lower_bound(same_ev, tgt, same_evlen)
      if a <= same_evlen and same_ev[a] == tgt then
        cnt = cnt + 1
      end
      a = lower_bound(evens, tgt, curmax_even)
      curmax_even = mmi(evlen, a)
      for k = a, evlen do
        if evens[k] == tgt then
          cnt = cnt + 2
        else break
        end
      end
    elseif tgt % 8 == 2 then
      local a = lower_bound(same_odd, tgt, same_oddlen)
      if a <= same_oddlen and same_odd[a] == tgt then
        cnt = cnt + 1
      end
      a = lower_bound(odds, tgt, curmax_odd)
      curmax_odd = mmi(odlen, a)
      for k = a, odlen do
        if odds[k] == tgt then
          cnt = cnt + 2
        else break
        end
      end
    elseif tgt % 4 == 1 then
      local a = lower_bound(evod, tgt, curmax_evod)
      curmax_evod = mmi(eolen, a)
      for k = a, eolen do
        if evod[k] == tgt then
          cnt = cnt + 2
        else break
        end
      end
    end
  end
end
print(cnt)
0