「三日坊主にならないようにがんばるぞ!」なブログ

三日坊主にならないようにがんばるぞ!

AtCoder用のローカル環境

形から入るタイプなのでAtCoderをはじめる前に下記のonline-judge-toolsとatcoder-cliをベースに環境を作りました。 online-judge-tools.readthedocs.io tatamo.81.la

ただ、online-judge-toolsで生成されるテスト問題用ディレクトリの名前と、atcoder-cliで読み込みに行くテスト問題用ディレクトリの名前が異なっているようなのでgithubのコードを元にフォルダ名が統一されるように書き直しました。

上記をより効率的に使うために.zshrcで下記のエイリアスを設定。main.pyが解答用コード、template.pyがテンプレ、sublはsublimeエイリアスです。
(英語のコメントは文法が適当かも)

#### for atcoder
# check if current dir is atcoder problem dir
function atchk() {
  # dirname of parent of parent of current
  ATDIR=$(basename $(dirname $(dirname $PWD)))
  if [ $ATDIR != "atcoder" ]; then
    echo "invalid directory"
    # source中で単にexitするとシェルが終了してしまう
    return 1 2>&- || exit 1
  fi
}

# execute test
alias attest="atchk && oj t -c \"python main.py\""

# create template file
alias atmain="atchk && atmain_func"
function atmain_func() {
  if [ -e main.py]; then
    echo "main.py already exists."
  else
    cp ../../template.py main.py
    subl main.py
  fi
}

# open problem page
alias atopen="atchk && atopen_func"
function atopen_func() {
  CONTEST=${$(dirname $PWD)##*/}
  PROBLEM=$(basename $PWD)
  command open "https://atcoder.jp/contests/${CONTEST}/tasks/${CONTEST}_${PROBLEM}"}

alias atready="atchk && atopen && atmain"
alias atsubmit="atchk && acc submit main.py"

実際に問題を解くときは、下記の流れでやってます。

  • 1.> acc new abc140 (テスト用のディレクトリを作成してテストデータ等をダウンロード+格納)
  • 2.> cd abc140/a (問題のフォルダに移動)
  • 3.> atready (テンプレから解答用コードを作成してSublimeで開き、合わせて問題のページをブラウザで開く)
  • 4.(コードを書く)
  • 5.> attest (各テストケースを試す)
  • 6.> atsubmit (コードを提出する)

ちなみに現時点のテンプレのソースは先人のテンプレも参考にしつつ以下を使っています(他記事のソースコードでもたまにテンプレの消し忘れ有り)。
ABC141で学んだヒープソートなど、抜けていた知識をこれからどんどん放り込んでいきます(意気込み)。 適当な引数を加えて実行(python ***.py 1 とか)することでデバッグモードに切り替え、IPython.embed()で対話できるようにしています。

railsでもbinding.pryを多用していたのでpythonでもなんとかならないかと思いたどり着きました。
(if em: embed()を対話したい箇所に挿入)

#!/usr/bin/env python3
import sys
# import math
# import numpy as np
# from functools import lru_cache

args = sys.argv
if len(args) == 2:
  from IPython import embed
  em = True
else:
  em = False

# sys.setrecursionlimit(10000)

#### input
# a, b = map(int, input().split())
# a = list(map(int, input().split()))
# a = list(map(lambda x: int(x)*(-1), a))  # 各要素を-1倍

# n = int(input())
# t = [int(input()) for i in range(n)]
if em: sys.stdin = open('/dev/tty')

#### function
# @lru_cache(maxsize=10000)

#### process
# if em: embed()

## heapsort, O(NlogN)
# import heapq
# heapq.heapify(A)
# min = heapq.heappop(A)
# heapq.heappush(A, new_element)