LoginSignup
5
0

AtCoderのFortranでfortran-stdlibが使えるようになったので何が楽になるかを考える

Last updated at Posted at 2023-12-11

AtCoderとは?

競技プログラミングを主催している会社.
そこでは毎週土曜日くらいの21:00からプログラミングコンテストが開かれているとか.

参考

ログインすればAtCoder上のコードテストでこの記事のコードを実行できる.
https://atcoder.jp/contests/practice/custom_test
ログインしないならこっち.
https://play.fortran-lang.org/

Fortranとは?

  • 主に大規模数値計算で使われる言語.
  • 速い
  • 組み込みには連想配列や可変長配列どころかソートすらない.

fortran-stdlibとは?

Fortran-langコミュニティが実装しているライブラリ.

AtCoderではこの前(2023年夏頃)の言語アップデートで使えるようになった(参考: https://img.atcoder.jp/file/language-update/language-list.html).

参考

何ができそうか

implicit_none さんの記事をじーっと見る.

とりあえずバージョンを調べる.

program check_version
  use stdlib_version
  implicit none
  write(*, *) stdlib_version_string
end program

結果
入力
(なし)
出力
0.2.1

ソート

  • AtCoderではソートした方が考えやすい問題が出題されることある(頻出?).
    • 順序を無視しても解が変わらない問題.
    • 小さい方(大きい方)から貪欲に処理する問題.
    • 配列上の2分探索.
      など

use stdlib_sorting して call sort(arr) をするだけ!

program sort_problem
  use stdlib_sorting
  implicit none
  integer :: arr(5) = [5, 3, 4, 2, 1]
  call sort(arr)
  write(*, *) arr(:)
end program sort_problem

結果
入力
(なし)
出力
1 2 3 4 5

文字列

  • AtCoderでは長さが正確に分かっていない文字列を入力とする問題が出題されることもあるので, character(len=200000) のように文字の長さを決め打ちする必要がある.
    • 文字列型に入力を読み込むことで, 長さの決め打ちを止めたいが...
    • type(string_type) の入力に問題があるらしく, AtCoderの入力を読み込むことはできないかもしれない...
    • 下のソースコードでは改行がないので, 入力の途中で End of file に到達してエラーになる.
program string_problem
  use stdlib_string_type
  implicit none
  type(string_type) :: str
  read(*, *) str
  write(*, *) str
end program string_problem

結果
入力
hello
(改行1つ)
出力
エラー

入力
hello

(改行2つ)
出力
hello

fortran-stdlibのドキュメントをじーっと見る

連想配列

  • AtCoderでは連想配列は言語に備わっていて当然のような雰囲気がある(偏見?).
    • 文字列の種類数を求められる.
    • 10^9などの巨大なインデックスに対応する配列のように扱える.
    • 数値が既に存在しているかを調べられる.
      など, 多様な使いみちがある.

Fortran-stdlibでの連想配列は以下のように使うことができる.
連想配列のキーcharacterinteger(int8)の配列 を使うことができ, はなんでもOK.

program hashmap_problem
  use stdlib_hashmaps 
  use stdlib_hashmap_wrappers
  implicit none
  type(chaining_hashmap_type) :: m
  type(key_type) :: key
  type(other_type) :: val
  call m%init(fnv_1_hasher)
  call set(key, "hello")
  call set(val, 5)
  call m%map_entry(key, val)
  call m%get_other_data(key, val)
  select type(v => val%value)
    type is (integer)
      write(*, *) v
  end select
end program hashmap_problem

入力
(なし)
出力
5

結論

  • ソートは楽に使える.
  • ハッシュマップは...可能性は未知数である.
    • 使うのに慣れが必要であろう.
    • 実装に class(*), allocatable が使われているため速度の確認も必要かもしれない.
5
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
5
0