2024年6月21日金曜日

Pythonで地図を扱う(folium)

foliumを使う

Pythonで地図を扱う方法は色々ありますが、今回はwebで扱いやすくデータを容易にプロット出来るfoliumを使ってみたいと思います。
 pip install folium 

 folium.__version__ 

 0.16.0
 #!/usr/bin/env python
# -*- coding: utf-8 -*-

import folium
import os

# ①
mp = folium.Map()

# ② htmlとして保存
html = "map.html"
# 使用するwebブラウザ
browser = "chrome "

# マップをhtmlに保存
mp.save(html)

# webブラウザで表示
os.system(browser + html)
使い方自体はとても簡単で、たった1行でマップが生成出来ます。# ①



生成は簡単ですが、htmlを保存してwebブラウザに表示するためのコードが# ②以下のコードです。
foliumオブジェクトのsave関数で保存し、os.systemコマンドでwebブラウザにすぐに表示出来るようにしています。
osライブラリを使うためにimport osをしています。


緯度経度で場所を指定

これだけだとどこを表示したいのか分からないので、多くは緯度経度をして使用します。
#!/usr/bin/env python
# -*- coding: utf-8 -*-

import folium
import os

# 緯度経度の指定 (この例では東京駅)
latlng = [35.682012250347064, 139.76718125374543]

# ①
mp = folium.Map(location=latlng, zoom_start=14)

html = "map2.html"
mp.save(html)
os.system("chrome " + html)
緯度経度は、Google Mapから場所を指定して右クリックしたりして取得してください。


locationは地図の中心にする場所の緯度経度をリストで指定し、zoom_startは倍率を指定します。
これはGoogle Map APIなど他のマップサービスでもよくある指定方法なので、分かりやすいですね。

2024年6月16日日曜日

Pythonでランダムな文字列生成

Pythonでランダムな文字列を生成する関数です。 

Pythonでデータフレームなどを扱う際、とりあえずダミーデータなどで試したい時に、適当な文字列があればと思い作りました。


 #!/usr/bin/env python
# -*- coding: utf-8 -*-

import random
import string

# numは生成する数、strsはその文字列からランダムに選択、lengthは一つの文字列の長さ
def word_generate(num, strs=string.ascii_lowercase, length=5):
    words = []
    for i in range(num):
        word = ""                        # ①
        for j in range(length):          # ①
            word += random.choice(strs)  # ①
        words.append(word)
    return words

print("[word generate]")
print("")

#アルファベット小文字
let = string.ascii_lowercase

print(let)
print("")

words1 = word_generate(5)
print(words1)
print("")

#よく使われる上位文字
let2 = 'etaonirsh'

words2 = word_generate(10, let2)
print(words2)
print("")

words3 = word_generate(5, let2, 8)
print(words3)
print("")
 

結果:

abcdefghijklmnopqrstuvwxyz

['lpiil', 'akoqp', 'bstzb', 'cteta', 'alyvd']

['ootot', 'sseni', 'nnntn', 'nhieh', 'rhnon', 'rsiat', 'aostn', 'rsert', 'reern', 'oittn']

['iitniess', 'oinshhri', 'raseoino', 'eniohoht', 'iasrsntr']


①の部分をchoiceからchoicesに変え        

word = "".join(random.choices(strs, k=length))

と書き換えても同じ結果になります。

2024年6月4日火曜日

NBAの平均得点の変遷

NBAのデータを調べてみたいと思い、年間平均得点の推移を出してみます

元データはNBA データAPIかKaggle辺りでゲームスコアの記録を見つけてきます。

1950年くらいから現在までの推移を見てみます。

#! /usr/bin/env python
# -*- coding:utf-8 -*-

import pandas as pd
import numpy as np
import matplotlib.pyplot as plt


data_file = "data/teams_data.csv"
df = pd.read_csv(data_file)

print("[NBA average score per year]")

# ゲームをシーズンごとのグループに分けます
season_score = df.groupby('season')

# シーズンを入れるリスト
years = []
# 平均得点を入れるリスト
average_score = []

for y, stat in season_score:
	years.append(y)
    average_score.append(stat['PTS'].mean())
    
plt.figure(figsize=(16, 6))
plt.grid()
plt.plot(year, average_score)
plt.show()

結果

これを見るとまだ3Pルールがない1960年~1970年辺りが高く、そこから下がっていき2000年代辺りが低くなってまた増加傾向にあるのが分かります。

レギュレーションや戦術の移り変わりが反映されてるのでしょう。

2024年4月15日月曜日

Easy PBR を使ってマテリアルを増やす 2【blender】

 準備が出来たら[Shading]タブを選択し、Nキーを押すと横から[EPBR]のタブが出てくるので、そのタブを選択してから、上のツリー好きな素材を選びます。

素材を選んだら、下の[↓]アイコン(Download This Shader)を押し解像度を選択します。



好きな解像度を選び[OK]を押すとマテリアルのダウンロードが始まり、終了すると[+]ボタンが押せるようになるので押すと適用されました。













Easy PBR を使ってマテリアルを増やす【blender】

Blenderでマテリアルをすべて自分で作るのは至難の業です。

簡単に質感が出せるBlenderのアドオンEasy PBRを使ってみましょう。

まずEasy PBRのサイトから右のフォームに『0』を入力、寄付する場合は任意の価格で下の購入ボタンを押します。




するとメールアドレス登録欄が出るので自分のメールアドレスを入れます。



するとダウンロード欄に行くのでBlender 3の場合は「EasyPBR__0.9.3__Beta.zip」「EPBR_library.zip」ファイルをダウンロードします。



ダウンロードしたファイル「EPBR_library.zip」は解凍し「Easy_PBR_library」フォルダにしてから任意のフォルダに入れてください(分かりやすいようにblender\assetなど)

そうしたら準備完了! Blenderを起ち上げてから[Edit]→[Preferences]→[Add-ons]と通常のアドオンを入れる手順から右上の[Install]を押すとBlender File Viewウインドウが開くので先ほどの任意のフォルダを開きます。



そして先ほどのzipファイル「EasyPBR__0.9.3__Beta.zip」を選択し


「Material: Easy PBR」にチェックを入れ、矢印を展開すると下に「PBR Library Path:」という欄があるので、先ほど解凍した「Easy_PBR_library」フォルダを選択し[Accept]を押します。



左下の[Save Preferences]を押しセット完了です。




2022年12月2日金曜日

サイコロ振って中心極限定理を確かめる

 中心極限定理とは、

中心極限定理は標本平均と母平均との誤差を論ずるものである。多くの場合、母集団の分布がどんな分布であっても、その誤差は標本の大きさを大きくしたとき近似的に正規分布に従う。wikipedia

とあるように標本を大きくしていくと正規分布に近づくという定理です。

サイコロを想定してpythonで表現してみます。

numpyのrandintでランダムに1〜6の目を出すサイコロを回数分出します。

とりあえず10000回くらい振ってみましょう。

#! /usr/bin/env python

# -*- coding:utf-8 -*-

import pandas as pd
import numpy as np


print("[dice]")
print()

# サイコロの目(1〜6)をランダムにnumpy配列で出力
pip = np.random.randint(1, 7, 10000)

# 作られた配列の先頭を表示
print(pip[:10])
print()
print(f"平均値: %f" % pip.mean())
print()

そしてmatplotlibのヒストグラムで分布を見てみましょう。

#ヒストグラムでプロット
import matplotlib.pyplot as plt
import japanize_matplotlib

plt.title("サイコロ")
plt.xlabel("出た目")
plt.ylabel("出た回数")
plt.hist(pip, bins=6, ec="k")
plt.show()

平均値: 3.502500
1~6までほぼ同じ回数出てるのが分かります。
期待値は(1+2+3+4+5+6) / 6 = 7/2 = 3.5なので平均値もほぼ合ってます。
サイコロ1つなら感覚的にもつかみやすいでしょう。

次に2個のサイコロを振ってみます。



import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
import japanize_matplotlib
#最瀕値を出すために使用
import statistics

#振る回数
roll = 10000

#1つ目のサイコロ
pip = np.random.randint(1, 7, roll)
#2こ目のサイコロの
pip2 = np.random.randint(1, 7, roll)

print("[dice]")
print()
#先頭10回分の目
print(pip[:10])
print(pip2[:10])

sm = pip + pip2
print()
print(f"平均値: %f" % sm.mean())
print(f'最瀕値: %f' % statistics.mode(sm))

plt.title("サイコロ")
plt.xlabel("出た目")
plt.ylabel("出た回数")
plt.hist(sm, bins=11, ec="k")

plt.show()

平均値: 7.044900

最瀕値: 7.000000


サイコロを2つにすると足した7が一番多い山のような形になることが分かります。




振るサイコロ6個の目の合計ではどうでしょう?

サイコロ6つだと、出る目は6の6乗の46656とおりになるので、それ以上回数を振らないとまばらな結果になりそうです。

10万回くらい振ってみましょう

#! /usr/bin/env python

# -*- coding:utf-8 -*-

#
import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
import japanize_matplotlib
#最瀕値を出すために使用
import statistics

#振る回数
roll = 100000

# ndarrayの初期化
sm = np.zeros(roll)

print("[dice]")


for i in range(6):
    pip = np.random.randint(1, 7, roll)
    
    #出ための先頭10回
    print(pip[:10])
    sm += pip

print()
print(f"平均値: %f" % sm.mean())
print(f"最瀕値: %f" % statistics.mode(sm))
print()
#出ための合計の種類
print(np.unique(sm))


plt.figure(figsize=(10, 8))
plt.title("サイコロ")
plt.xlabel("出た目の合計")
plt.ylabel("出た回数")
plt.grid()
plt.hist(sm, bins=31, ec="k")

plt.show()

平均値: 21.013420

最瀕値: 21.000000



ほぼ正規分布に近づきました。

標本を大きくすれば正規分布に近づいていくという中心極限定理が感覚的につかめました。

2022年11月19日土曜日

form要素のinput type="button" と button要素のJavaScriptでの挙動の違い

 フォーム要素でボタンを使用する場合、現在ではbutton要素が推奨されてます。

理由はそこら中で書いてありますが、CSSで疑似要素が使えたり、デザイン性で柔軟だからです。

ここではJavaScriptによる違いを書きます。


まずは、何もないbutton要素

  

何も指定しないと、type="submit"と同じ送信になり、formのaction属性と同じになります。

なのでtype="button"にしたい場合は属性を書かなければなりません。

button要素の中のテキストを取得したい場合は、input要素のようにvalueでは取得できません。button要素の文字は、タグで挟まれてるのでtextContentで取得します。


button要素でカウンターを作る例

  

冷静に考えたら分かりますね。

submitで値を送信したい場合は、そのままvalue属性が書けます。

NBAの1試合平均チームスタッツ (2025-26レギュラーシーズン)

前回 の元となったデータ、チーム毎の各スタッツ平均です。   team games w l win% PTS AST BLK STL ...