LoginSignup
1
2

More than 3 years have passed since last update.

スプレッドシートで各要素の掛け合わせの表を作る (Python)

Last updated at Posted at 2020-11-05

前提条件

次のような Python ディクショナリ型 の値をスプレッドシートに表の形で記述する場合。

    pattern = {
        'エリア': ['日本', 'アメリカ', 'イギリス'],
        '性別': ['男', '女'],
        '身長': ['100cm以上', '100cm未満']
    }

環境

  • Python 3.7.6
  • Linux

掛け合わせ表の作成 (直積)

スプレッドシートで次のような各要素を掛け合わせた表を作りたい場合、

エリア 性別 身長
1 日本 100cm以上
2 日本 100cm未満
3 日本 100cm以上
4 日本 100cm未満
5 アメリカ 100cm以上
6 アメリカ 100cm未満
7 アメリカ 100cm以上
8 アメリカ 100cm未満
9 イギリス 100cm以上
10 イギリス 100cm未満
11 イギリス 100cm以上
12 イギリス 100cm未満

Python で次のように書くと、カンマ区切りのものが出力されるので

from itertools import product

if __name__ == '__main__':
    pattern = {
        'エリア': ['日本', 'アメリカ', 'イギリス'],
        '性別': ['男', '女'],
        '身長': ['100cm以上', '100cm未満']
    }
    delimiter = ','
    result = delimiter + delimiter.join(pattern.keys()) + '\n'
    i = 0
    for item in product(*pattern.values()):
        i += 1
        result += str(i) + delimiter + delimiter.join(item) + '\n'
    print(result)

それをスプレッドシートに貼り付けるとうまい具合に表ができます。

,エリア,性別,身長
1,日本,男,100cm以上
2,日本,男,100cm未満
3,日本,女,100cm以上
4,日本,女,100cm未満
5,アメリカ,男,100cm以上
6,アメリカ,男,100cm未満
7,アメリカ,女,100cm以上
8,アメリカ,女,100cm未満
9,イギリス,男,100cm以上
10,イギリス,男,100cm未満
11,イギリス,女,100cm以上
12,イギリス,女,100cm未満

補足

  • itertools.product を使って、 複数のリストの掛け合わせを作っています。 この関数は可変長引数ですから、 *pattern.values() と書いてリストを展開する書き方にしています。
  • for の中で使う iemumerate を使って作ることもできます。 次のコードでは enumerate を使っています。

分類項目表の作成

上の掛け合わせ表の各項目とその値について次のような表を作りたい場合

項目
エリア 日本
アメリカ
イギリス
性別
身長 100cm以上
100cm未満

Python で次のように書くと、カンマ区切りのものが出力されるので

if __name__ == '__main__':
    pattern = {
        'エリア': ['日本', 'アメリカ', 'イギリス'],
        '性別': ['男', '女'],
        '身長': ['100cm以上', '100cm未満']
    }
    delimiter = ','
    result = ''
    for key, value in pattern.items():
        for index, item in enumerate(value):
            if index == 0:
                result += key
            result += delimiter + item + '\n'
    print(result)

それをスプレッドシートに貼り付けるとうまい具合に表ができます。

エリア,日本
,アメリカ
,イギリス
性別,男
,女
身長,100cm以上
,100cm未満

まとめたコード

これを対話型で進められるひとつのPythonファイルにすると次のようになります・

from itertools import product

def get_input(default: str = ''):
    value: str = input().rstrip("\n")
    if value:
        return value
    return default

def configure():
    print("""
Please configure
    delimiter [,]:
""")
    delimiter = get_input(',')

    print(f"""
    prefix:
    """)
    prefix = get_input()

    print(f"""
    suffix:
    """)
    suffix = get_input()
    return delimiter, prefix, suffix

def print_product_table(pattern: dict, delimiter: str, prefix: str, suffix: str):
    result = prefix + delimiter + delimiter.join(pattern.keys()) + suffix + '\n'
    i = 0
    for item in product(*pattern.values()):
        i += 1
        result += prefix + str(i) + delimiter + delimiter.join(item) + suffix + '\n'
    print(result)

def print_category_key_value(pattern, delimiter, prefix, suffix):
    result = ''
    for key, value in pattern.items():
        for index, item in enumerate(value):
            line = prefix
            if index == 0:
                line += key
            line += delimiter + item + suffix
            result += line.strip() + '\n'
    print(result)

if __name__ == '__main__':
    pattern = {
        'エリア': ['日本', 'アメリカ', 'イギリス'],
        '性別': ['男', '女'],
        '身長': ['100cm以上', '100cm未満']
    }

    print_pattern: int = None
    while True:
        print("""
Print dict structure.

Enter print pattern:
    1. Product table
    2. Category key-value
        """)
        print_pattern = int(get_input())
        if print_pattern in [1, 2]:
            break;

    delimiter, prefix, suffix = configure()

    if print_pattern == 1:
        print_product_table(pattern, delimiter, prefix, suffix)
    elif print_pattern == 2:
        print_category_key_value(pattern, delimiter, prefix, suffix)

その他

なぜ Python なのか
ちょうどそのとき Python 使って作業していたからです。
1
2
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
1
2