PyCharm: Terminal のシェルの変更
PyCharm のデフォルトのシェルは cmd.exe です。
これを PowerShell.exe に変更する手順です。
1. [Files] - [Settings]
2. [Tools] - [Terminal]
3. "Shell path" に "PowerShell.exe" と入力し、[OK] を押します。
普段使用している PowerShell のプロファイルを読み込まないようにするためには、以下のコマンドを登録すると良いです。
PowerShell.exe -NoProfile
以上です。
PyCharm: パッケージをオフラインで追加する
前回、PyCharm のパッケージを GUI からインストールしました。GUI からのインストールは簡単で便利だったのですが、インターネットに接続している必要があります。
PyCharm: Pythonパッケージの追加 - あれやこれや
今回は予め資源をダウンロードしておき、オフラインでインストールをしてみたいと思います。
1. インストール用のパッケージを入手する
まずは、 PyPI で必要な資源をダウンロードします。
以下にアクセスします。
以下のような画面が表示されます。検索欄にインストールしたいパッケージ名を入力し、検索をします。 今回の例では、PySimpleGUI を検索します。
検索結果から必要なパッケージのリンクをクリックします。今回の例では、"PySimlpeGUI 4.35.0" をクリックします。
"PySimlpeGUI 4.35.0" のページが開きます。左の欄にある "Download files" をクリックします。
パッケージのダウンロード画面になりますので、パッケージをダウンロードします。
今回は、"PySimpleGUI-4.35.0-py3-none-any.whl" をダウンロードしました。
※ "PySimpleGUI-4.35.0.tar.gz" でもインストールは可能です。
2. パッケージをインストールする
PyCharm を起動します。そして、赤枠部分にある "Terminal" をクリックします。
CLI が起動します。
先ほどダウンロードした資源の格納されているディレクトリへ移動後、以下のコマンドを実行します。
pip install .\PySimpleGUI-4.35.0-py3-none-any.whl
これでインストール完了です。
3. インストール状態の確認
"pip list" コマンドで確認するとこんな感じです。
GUI で確認すると、こんな感じです。
以上です。
PyCharm: Pythonパッケージの追加
PyCharm 環境にパッケージを追加する手順をまとめました。
今回は、Pillow を追加してみようと思います。
1. パッケージがインストールされていないことを確認する
まずは、Pillow が動作しないことを確認してみます。
パッケージでインポートしようとすると、エラーになります。当然です。
別の方法として、[File] - [Settings] - [Python Interpreter] をすると、インストールされているパッケージが表示されます。Pillow がインストールされていないので、表示されていません。
2. パッケージのインストール
それでは、Pillow パッケージをインストールします。
1. [File] - [Settings] をクリックします。
2. [Python Interpreter] から追加画面を表示します。
[Python Interpreter] を選択し、さらに、赤枠部分の "+" をクリックします。
3. パッケージ名を検索し、インストールをします。
検索欄にパッケージ名を入力します。今回は "pillow" と入力します。
インストール対象 ("Pillow") を選択し、[Install Package] をクリックします。
4. インストールが完了すると、緑色で "installed successfully" と表示されます。
3. インストール確認
1. [Python Interpreter] の画面に "Pillow" が表示されていることが分かります。
2. スクリプトで import してみると、エラーが表示されなくなりました。
以上でございます。
タブで 2つの Frame の切り替えができるようにしようとしたら、Frame が2つ縦に並んでしまった件 (とりあえず解決)
タブを 2つ用意し、そのタブ毎にフレームを作成して、タブでフレームを切り替えられるようにしようとしたところ、こんな感じになってしまいました。
なんというか、Frame がタブに収まってないって感じです。
フレーム作成の共通の処理をするために BaseFrame というクラスを作成したのですが、このクラスに問題があるらしく、BaseFrame クラスを経由しなければうまくいく、というのが前回分かりました。
さて、問題の BaseFrame クラスですが、以下のようなものです。
class BaseFrame(tk.Frame):
def __init__(self, master):
frame_color = "lightskyblue"
# call constructor
super().__init__(master, relief="groove", bd=6)
self.base_frame = tk.Frame(master,
bg=frame_color,
relief="sunken", bd=5)
self.base_frame.grid()
# put label
self.r0c0_label = tk.Label(self.base_frame, font=("system"),
text="path: ", anchor="w", padx=1, width=10)
self.r0c0_label.grid(row=0, column=0, sticky="w")
# put entry
self.r0c0_entry = tk.Entry(self.base_frame, width=50, bd=2, font=("system"))
self.r0c0_entry.grid(row=0, column=0, columnspan=2, padx="60", sticky="w")
self.r1c0_button = tk.Button(self.base_frame, text="put button",
command=lambda obj=self.r0c0_entry:
run_script(obj)
)
self.r1c0_button.grid(row=1, column=0, pady=5, sticky="w")
Python のマニュアルを改めてみてみると、Frame クラスを継承したクラスのサンプルは以下のように記載されています。
tkinter --- Tcl/Tk の Python インタフェース — Python 3.9.1 ドキュメント
私との違いは、tk.Frame の生成のところです。Python のマニュアルは、tk.Frame の __init__ を実行後、すぐ、self.pack() をしています。App は、tk.Frame を継承しているので、self 自体が tk.Frame なんですね。だから、self.pack() でよいのだということなのでしょう。
私の場合、BaseFrame(tk.Frame) の中で、さらに tk.Frame をインスタンス化していたので、この部分が冗長でした。そこで、BaseFrame(tk.Frame) の BaseFrame.base_frame 記述を self に置き換えることにしました。
ここの部分です。
self.base_frame = tk.Frame(master,
bg=frame_color,
relief="sunken", bd=5)
self.base_frame.grid()
以下のように直しました。
super().__init__(master, relief="groove", bg=frame_color, bd=5)
# 修正: tk.Frame を呼ぶ必要がない。なぜなら、tk.Frame を継承しているから。
# self.base_frame = tk.Frame(master,
# bg=frame_color,
# relief="sunken", bd=5)
# 自分自身を grid する
# self.base_frame.grid()
self.grid()
その結果、
うまく動作しました。
・修正後のコード
import tkinter as tk
import tkinter.ttk as ttk
class BaseFrame(tk.Frame):
def __init__(self, master, button_text=None):
frame_color = "lightskyblue"
# call constructor
super().__init__(master, relief="groove", bg=frame_color, bd=5)
# 修正: tk.Frame を呼ぶ必要がない。なぜなら、tk.Frame を継承しているから。
# self.base_frame = tk.Frame(master,
# bg=frame_color,
# relief="sunken", bd=5)
# 自分自身を grid する
# self.base_frame.grid()
self.grid()
# 以下、self.base_frame を parent にしていた部分を self へ置き換える
# put label
self.r0c0_label = tk.Label(self, font=("system"),
text="path: ", anchor="w", padx=1, width=10)
self.r0c0_label.grid(row=0, column=0, sticky="w")
# put entry
self.r0c0_entry = tk.Entry(self, width=50, bd=2, font=("system"))
self.r0c0_entry.grid(row=0, column=0, columnspan=2, padx="60", sticky="w")
self.r1c0_button = tk.Button(self, text=button_text,
command=lambda obj=self.r0c0_entry:
run_script(obj)
)
self.r1c0_button.grid(row=1, column=0, pady=5, sticky="w")
def run_script(entry=None):
url = entry.get()
print(url)
class MainWindow:
def __init__(self):
self.root = tk.Tk()
self.root.title("GUI")
self.root.attributes("-topmost", True)
# -----------------------------------
# Notebook を使ってタブを設定してみる
# -----------------------------------
notebook = ttk.Notebook(self.root)
notebook.grid(sticky="w")
# tab に表示する frame1 と frame2 を生成する。
# タブの切り替えが分かるように button のテキストを変えられるようにする
self.frame1 = BaseFrame(master=self.root, button_text="button1")
self.frame2 = BaseFrame(master=self.root, button_text="button2")
# notebook に追加する
notebook.add(self.frame1, text="tab1")
notebook.add(self.frame2, text="tab2")
# 変更はここまで ------------------------
self.root.mainloop()
# start program
MainWindow()
if __name__ == '__main__':
pass
ちなみに、逆に BaseFrame を呼び出す側で、notebook.add() に BaseFrame.base_frame を指定すればいいんじゃない ? というのも思ったので、やってみると....
できました !
・コード
import tkinter as tk
import tkinter.ttk as ttk
class BaseFrame(tk.Frame):
def __init__(self, master, button_text):
frame_color = "lightskyblue"
# call constructor
super().__init__(master, relief="groove", bd=6)
self.base_frame = tk.Frame(master,
bg=frame_color,
relief="sunken", bd=5)
self.base_frame.grid()
# put label
self.r0c0_label = tk.Label(self.base_frame, font=("system"),
text="path: ", anchor="w", padx=1, width=10)
self.r0c0_label.grid(row=0, column=0, sticky="w")
# put entry
self.r0c0_entry = tk.Entry(self.base_frame, width=50, bd=2, font=("system"))
self.r0c0_entry.grid(row=0, column=0, columnspan=2, padx="60", sticky="w")
self.r1c0_button = tk.Button(self.base_frame, text=button_text,
command=lambda obj=self.r0c0_entry:
run_script(obj)
)
self.r1c0_button.grid(row=1, column=0, pady=5, sticky="w")
def run_script(entry=None):
url = entry.get()
print(url)
class MainWindow:
def __init__(self):
self.root = tk.Tk()
self.root.title("GUI")
self.root.attributes("-topmost", True)
# -----------------------------------
# Notebook を使ってタブを設定してみる
# -----------------------------------
notebook = ttk.Notebook(self.root)
notebook.grid(sticky="w")
# tab に表示する frame1 と frame2 を生成する
self.frame1 = BaseFrame(master=self.root, button_text="b1")
self.frame2 = BaseFrame(master=self.root, button_text="b2")
# notebook に追加する
# 変更: 追加する対象を BaseFrame.base_frame にする
notebook.add(self.frame1.base_frame, text="tab1")
notebook.add(self.frame2.base_frame, text="tab2")
# 変更はここまで ------------------------
self.root.mainloop()
# start program
MainWindow()
if __name__ == '__main__':
pass
でも、こっちは階層が深くなって分かりにくい感じがします。
今日はここまでです。
PyCharm: メニューの文字の大きさを変更する
PyCharm のメニューの文字がちょっと小さく感じたので、大きくする方法を調べました。
対象は、以下の赤枠のところです。
・手順
1. [File] - [Settings] を選択します。
2. [Appearance] を選択します。
デフォルトの文字のサイズは "12" になっています。
3. 文字サイズの設定
"User custom font" の左側のチェックボックスにチェックを入れ、"Size" で文字サイズを入力します。"Apply" を押すと、文字の大きさが変わります。ちょうどよい大きさになったら、"OK" を押します。
4. メニューの文字が大きくなったことを確認します。
以上です。
PyCharm: インストールと起動
PyCharm のインストールから起動までの手順を記載します。
1. PyCharm のインストール
インストールは簡単です。
公式サイトからダウンロードしてインストーラを実行すれば完了です。
1. PyCharm のダウンロード
公式ホームページにアクセスすると、中央に "ダウンロード" の記載があります。
https://www.jetbrains.com/ja-jp/pycharm/
真ん中の "ダウンロード" をクリックします。
今回はコミュニティ版をダウンロードしますので、黒色で書かれた "ダウンロード" をクリックします。 任意のフォルダにインストーラをダウンロードします。
以下の画面では特に何もしなくとも問題ありません。
2. インストーラの実行
ダウンロードしたインストーラをダブルクリックします。
"Next" をクリックします。
"Next" をクリックします。
"Create Desktop Shortcut", "Update PATH variable", "Update context menu" など必要な項目にチェックをいれて、"Next" をクリックします。
"Install" をクリックすると、インストールが始まります。
インストールに時間はかかりません。
"Finish" を押したら、PCを再起動します。これで完了です。
2. PyCharm の起動
1. デスクトップのショートカットから起動します。
2. 始めのプロジェクトを作成するので "New Project" をクリックします。
3. "Location" にプロジェクトの格納フォルダを指定して、"Create" をクリックします。
4. プロジェクトの作成が始まります。
5. 以下の画面が表示されれば完了です。
チェックリスト: Azure Storage のデータ冗長性オプション
今日は Azure の Storage に関する勉強です。
- 1. ローカル冗長ストレージ (LRS)
- 2. geo冗長ストレージ (GRS)
- 3. 読み取り geo冗長ストレージ (RA-GRS: Read-access geo-redundant storage)
- 4. ゾーン冗長ストレージ (ZRS)
- 5. geoゾーン冗長ストレージ (GZRS)
- 6. 読み取りアクセス geoゾーン冗長ストレージ (RA-GZRS)
- 他の用語
1. ローカル冗長ストレージ (LRS)
1つのデータセンタ内において、別々のラックに設置されている H/W 間でデータが 3回複製される。データの複製は、3つのレプリカ全てが正常に書き込まれた場合にのみ、正常と判断される。
・どのくらい安全か ?
特定のストレージ、電源ユニットなどで障害が発生してもサービスを継続することができる。
データセンタ単位やリージョン単位の障害には弱い。
2. geo冗長ストレージ (GRS)
GRS では、データは 1つのリージョン内で 3回、ペアになっているセカンダリリージョンで 3回コピーされる。
#疑問: GZRS の存在意義を考えると、GRS では、1つのリージョンに限って考えると、LRS と同じなのかもしれない。
・どのくらい安全か ?
プライマリリージョン全体を覆う障害が発生しても、セカンダリリージョンを使用してサービスを継続することができる。
3. 読み取り geo冗長ストレージ (RA-GRS: Read-access geo-redundant storage)
geo冗長ストレージのセカンダリリージョンからデータを読み取り可能にしたもの。
geo冗長ストレージ構成をとると、プライマリリージョンで障害が発生しない限り、セカンダリリージョンのデータを読み取ることができない。しかし、RA-GRS 構成をとると、セカンダリリージョンからデータの読み取りを行うことができるようになる。
# 詳細不明
4. ゾーン冗長ストレージ (ZRS)
プライマリリージョンの 3つの Azure 可用性ゾーン間でデータを同期的にコピーする。書き込み操作が 3つの可用性ゾーンのレプリカ全てに書き込まれた場合にのみ、正常と判断される。
・どのくらい安全か ?
LRS と同様に特定の電源ユニット、ストレージなどで発生した障害には強い。
データセンタ単位の障害に対しても対応できる。
リージョン全体を巻き込む災害があった場合には守れない。
5. geoゾーン冗長ストレージ (GZRS)
ZRS(ゾーン冗長ストレージ) と GRS(geo冗長ストレージ) の利点を組み合わせたもの。
データが1つのリージョン内の 3つの可用性ゾーン全体にコピーされる。かつ、セカンダリリージョンにも 3回複製が行われる。
対応リージョンは以下の通りである。
東南アジア
北ヨーロッパ
西ヨーロッパ
東日本
英国南部
米国中部
米国東部
米国東部2
6. 読み取りアクセス geoゾーン冗長ストレージ (RA-GZRS)
セカンダリリージョンへの読み取りアクセスを可能にした GZRS。
対応リージョンは以下の通りである。
東南アジア
北ヨーロッパ
西ヨーロッパ
東日本
英国南部
米国中部
米国東部
米国東部2
他の用語
Paired regions
GRS やGZRS のレプリケーションでは、リージョン単位での停止を回避するために、1つの Azureリージョンは別のリージョンとペアになっている。これを Paired regions と呼ぶ。
可用性ゾーン
リージョン内に存在する冗長性を管理する単位。それぞれの可用性ゾーンは、独立した電源、冷却手段、ネットワークを備えている。各リージョン内には、少なくとも 3つの可用性ゾーンが存在する。