エンターテイメント!!

遊戯王好きのJavaエンジニアのブログ。バーニングソウルを会得する特訓中。

Javaエンジニア向けのPython簡易まとめ

Python

主にJavaとの違いについて個人的なまとめ。
Javaよりも5年位前に誕生。
興味を持っているが、業務で使えないので、忘れないようにメモ。

概要

インデント

同じインデントの深さ = 同じブロック
タブとスペース混在しても大丈夫だが、危険。
(混ぜるな、危険だ!!)
文の終わりは、改行。

インタプリタ

コンパイル不要で、即実行。

マルチプラットフォーム

複数環境で動作する。
動作するプラットフォームに特化したライブラリが存在するのが、Javaと違うところ。

実行速度

C言語Javaに劣る。コンパイラ使わないので、仕方ない。
速度が必要な箇所は、局所化して、多言語を利用することを考える。
今後、速度が伸びる可能性は、大!

メモリ管理

ガーベージコレクション。Javaと一緒。

仕様策定

PEPで行う。(Javaで言うところのJCP)
下記のルールに従って、仕様が策定される。

  1. アイディア提出
  2. 仕様のドキュメント化
  3. レビュー
  4. 採用

型とリテラル

  • オブジェクト
  • 論理型
  • 数値型
    • int
    • flot
    • complex

シーケンス

オブジェクトを順番に処理するデータ構造

文字列

内部ではUnicodeで保持する。
基本的にはJavaと同じ。

リスト

Javaのリストと同じ。
複数の方を一つにまとめて、順序を保持する。
宣言は、"[]"を使用する。 要素の取得方法には、いくつか種類がある。

  • インデックス指定
    インデックス指定で値を取得
  • スライス
    開始と終了のインデックスを指定して、リストからサブリストを取得する。
  • イテレーション
    全要素に順次アクセス
['遊戯', '十代', '遊星', '遊馬', '遊矢']

タプル

イミュータブルなリスト。
イミュータブルなので、リストより高速。
宣言は、"()"を使用する。

('遊戯', '十代', '遊星', '遊馬', '遊矢')

セット

値を保持するが、順序は保持しない。
値は一意で不変。

{'遊戯', '十代', '遊星', '遊馬', '遊矢'}

辞書

キーと値を対応させたデータ構造。(JavaのMapと同じ)
順序は保証されない。

{'name':'遊戯', 'name':'十代', 'name':'遊星', 'name':'遊馬', 'name':'遊矢'}

None型

値が存在しないことを表す。(Javaのnullと同じような位置づけ)

制御構文

条件文

ほぼJavaと同じ。
偽(false)として扱われる値があるので、Javaエンジニアは注意が必要。
下記が偽と扱われる。

  • None
  • False
  • ゼロと認識できる数値
  • 空のシーケンス
  • 空のマップ、セット

ループ

インデントで範囲が決まるのが、どうしてもキモい。。。
慣れかも知れない。

for文

for x in ['遊戯', '十代', '遊星', '遊馬', '遊矢'] :
     print(x)

while文

sum = 0
while sum < 2:
    print("sum:" + str(sum))
    num += 1

例外処理

tryで始まる。
exceptで例外補足(Javaのcatch句に相当)
複数の例外の補足も可能。

try:
    a = 10 / 0
except ZeroDivisionError:
    print("Error!!")

else/finally

else → try句内で例外が発生せずに最後まで処理が進んだ場合の処理 finally → 例外の発生に関係なく、最後に必ず処理

例外のスロー

raiseで例外スロー
※raiseと言われると小倉唯を思い出すのは、声豚だから?

try:
    raise NameError('stop!!')
except NameError:
    print('show must go on')

関数

Javaのメソッドに相当。
定義は、以下の通り。

def 関数名 ( 引数 ):
   処理
   return 戻り値

呼び出す際に全ての引数を指定しないと例外が発生する。
ただし、デフォルト引数が指定されている場合は、省略可能。
定義は以下の通り。

def 関数名 ( 引数=値 ):
   処理
   return 戻り値

可変長引数

可変長引数が定義できるのは、Javaと一緒。
引数の前に"*"を付ける。

def 関数名 ( *引数 ):
   処理
   return 戻り値

global宣言

var1 = 'グローバル'

def spam():
    global var1
    var1 = 'カオスエクシーズチェンジ!'

spam()
print(var1)

「カオスエクシーズチェンジ」と表示される。
なに当たり前なこと言ってんだと思う場合、下記の例を見てみる。

var1 = 'グローバル'

def spam():
    var1 = 'カオスエクシーズチェンジ!'

spam()
print(var1)

この場合は「グローバル」と表示される。
意図的にグローバルを参照させたい場合は、グローバル宣言が必要になる。

nonlocal宣言

globalの逆。ローカル変数が外部からでも参照できるようになる。
クロージャに対応するために導入された。

関数デコレータ

Javaアノテーションを使ったAOP的なことができる

ドキュメンテーション文字列

Javadocと同じ。
Pythonのヘルプ機能で参照できたりもする。

関数アノテーション

Javaの引数アノテーションとほぼ同義。

クラス

基本的にはJavaと同じ。

定義

class クラス名:

アクセス

属性へのアクセス

インスタンス.属性名 = 値

メソッドアクセス

インスタンス.メソッド名

コンストラクタ

__init__で記述する。
コンストラクタの定義でいろいろ論争がある模様。
自分は、コンストラクタ_init()はコンストラクタでいいのではなかろうか派。

デコンストラクタ

インスタンスの削除。Javaにはない(あるにはあるけど、使うべきではないので、ないということにする)。
__del__で記述。
循環参照している場合は、インスタンスが解放されないので注意。

インスタンスアロケータ

__new__で記述。
コンストラクタで初期化した不変な変数の変更をする。
不要なら極力書かないのが暗黙のルール?

継承

Pythonは多重継承。
そのため、複雑な問題があるように感じる。

やり方

class Base: #基底クラス

class Child(Base) : # 派生クラス

なお、基底クラスの呼出しは、super()で行う。(Javaと同じ)

多重継承

定義方法

class クラス名(基底クラス[, 基底クラス・・・]) :

多重継承で呼び出すクラスが解決できない場合は、エラーになる。

mro()で検索順序を取得することが可能。

感じていること

基本的にベースとなる知識との違いを覚えておけば、簡単に覚えられる。
ただ、使う機会が少ないとすぐ忘れる。
見返して思い出したのがいくつかある。
いろんな言語に触れる習慣を作る必要があると感じた。
文法は、Javaで煩わしさを感じるところが楽にかける印象がある。