LoginSignup
0
0

.iniファイルに定義されていたリストを扱うときにエラー

Last updated at Posted at 2024-01-15

何が起きたか?

.iniから読み込んだリストの形をした文字列をlist()で変換したら期待外れな値が返ってきた。

解決方法

ast.literal_eval()を使う。

目次

  1. 問題の.iniファイル
  2. そのまま出力
  3. 間違ったやり方
  4. 正しいやり方
  5. ちなみに辞書も
  6. eval()の脆弱性

問題の.iniファイル

test.ini
[test]
target_l=[10,20,30]

そのまま出力

>>> import configparser

>>> config = configparser.ConfigParser()
>>> config.read('test.ini')

>>> target_l = config['test']['target_l']
>>> print(target_l)
'[10,20,30]' #文字列

文字列じゃなくてリストにしたい...

間違ったやり方

>>> import configparser

>>> config = configparser.ConfigParser()
>>> config.read('test.ini')

>>> target_l = list(config['test']['target_l'])
>>> print(target_l)
['[', '1', '0', ',', '2', '0', ',', '3', '0', ']'] #中身が一文字ずつ文字列に(汗)

正しいやり方

>>> import configparser
>>> import ast

>>> config = configparser.ConfigParser()
>>> config.read('test.ini')

>>> target_l = ast.literal_eval(config['test']['target_l'])
>>> print(target_l)
[10,20,30] 

ちなみに辞書も

test.ini
[test]
target_d={'a':'1', 'b':'2', 'c':'3'}
>>> import configparser
>>> import ast

>>> config = configparser.ConfigParser()
>>> config.read('test.ini')

>>> target_d = ast.literal_eval(config['test']['target_d'])
>>> print(target_d)
{'a':'1', 'b':'2', 'c':'3'}

ast.literal_eval()とeval()

今回の例では組み込み関数のeval()用いても同様な結果を得ることが可能です。
しかしeval()の主な用途は文字列をコマンドとして評価して実行することであるため、使用する際は注意が必要です。

eval("os.remove(test.py)")

一方、literal_eval()の場合は文字通りリテラルな文字列を対象とするため、別途定義された変数などを参照するとエラーを返してくれます。

0
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
0
0