Open GENZITSU opened 3 years ago
長いのでためになったところだけ抜粋。
# from https://qiita.com/baby-degu/items/05cf809d4d992923020d
numbers = [2, 4, 6, 8, 1]
for number in numbers:
if number % 2 == 1:
print(number)
break
else:
print("No odd numbers")
奇数が見つかった場合、breakを実行しelseブランチをスキップするため、その数字を出力します。それ以外はbreakを実行しないため、実行フローはelseブランチを実行します。
# from https://qiita.com/baby-degu/items/05cf809d4d992923020d
import heapq
scores = [51, 33, 64, 87, 91, 75, 15, 49, 33, 82]
print(heapq.nlargest(3, scores)) # [91, 87, 82]
print(heapq.nsmallest(5, scores)) # [15, 33, 33, 49, 51]
Enumは、一意の値にバインドされた識別名の集合です。グローバル変数と似ていますが、より便利なrepr()やグループ化、型安全性などの機能があります。
# from https://qiita.com/baby-degu/items/05cf809d4d992923020d
from enum import Enum
class Status(Enum):
NO_STATUS = -1
NOT_STARTED = 0
IN_PROGRESS = 1
COMPLETED = 2
print(Status.IN_PROGRESS.name) # IN_PROGRESS
print(Status.COMPLETED.value) # 2
# from https://qiita.com/baby-degu/items/05cf809d4d992923020d
x = 3
print (1 < x < 10) # True
# from https://qiita.com/baby-degu/items/05cf809d4d992923020d
books = ('Atomic habits', 'Ego is the enemy', 'Outliers', 'Mastery')
print(books.index('Mastery')) # 3
# from https://qiita.com/baby-degu/items/05cf809d4d992923020d
import ast
def string_to_list(string):
return ast.literal_eval(string)
string = "[[1, 2, 3],[4, 5, 6]]"
my_list = string_to_list(string)
print(my_list) # [[1, 2, 3], [4, 5, 6]]
# from https://qiita.com/baby-degu/items/05cf809d4d992923020d
print("29", "01", "2022", sep="/") # 29/01/2022
print("name", "domain.com", sep="@") # name@domain.com
# from https://qiita.com/baby-degu/items/05cf809d4d992923020d
print(1_000_000_000) # 1000000000
print(1_234_567) # 1234567
# from https://qiita.com/baby-degu/items/05cf809d4d992923020d
dictionary_one = {"a": 1, "b": 2}
dictionary_two = {"c": 3, "d": 4}
merged = {**dictionary_one, **dictionary_two}
print(merged) # {'a': 1, 'b': 2, 'c': 3, 'd': 4}
一押しは
さまざまな量子アルゴリズムで採用されている汎用的な量子回路について、量子ビットの数と量子回路の深さなどがモデルの表現力と過学習にどう影響するかを研究した。その結果、「量子回路の深さを増してパラメーターを増加させると、ある地点でモデルの表現力が飽和する」ことを数値実験で見いだした。
表現力の飽和は回路パラメーターを増加させても、それ以上モデルが複雑化せず、過学習が起きないことを意味する」(グリッド)。さらに理論保証として、モデルの複雑性の指標である「VC次元(学習モデルが完全に分類できる最大のデータ数を数値化したもの)」が上限値を持つことを証明した。
量子NNは過学習しづらいっぽいが、逆に言えばモデルの表現力に上限があるということよね...?
行末が心配だ...
顔認識ライブラリで結構新しめのモデルもカバーされている。
使い方に関してはこちらのzennの投稿がわかりやすい
# from https://zenn.dev/yuyakato/articles/6a1d8177901381
face_analysis = insightface.app.FaceAnalysis()
face_analysis.prepare(ctx_id=0, det_size=(640, 640))
@app.post("/detect")
async def post_detect(file: fastapi.UploadFile = fastapi.File(...)):
assert file.content_type == "image/jpeg"
image = PIL.Image.open(file.file).convert("RGB")
image = np.array(image)
image = image[:, :, [2, 1, 0]] # RGB to BGR
faces = face_analysis.get(image)
file.file.seek(0)
sha1_hash = hashlib.sha1(file.file.read()).hexdigest()
file_size = file.file.tell()
return {
"service": SERVICE,
"time": int(datetime.datetime.now().timestamp() * 1000),
"request": {
"file": {"name": file.filename, "size": file_size, "sha1": sha1_hash}
},
"response": {
"width": image.shape[1],
"height": image.shape[0],
"numberOfFaces": len(faces),
"faces": [
{
"score": face.det_score.astype(float),
"boundingBox": {
"x1": face.bbox[0].astype(float),
"y1": face.bbox[1].astype(float),
"x2": face.bbox[2].astype(float),
"y2": face.bbox[3].astype(float),
},
"keyPoints": [
{"x": xy[0].astype(float), "y": xy[1].astype(float)}
for xy in face.kps
],
"landmarks": {
"2d_106": [
{"x": xy[0].astype(float), "y": xy[1].astype(float)}
for xy in face.landmark_2d_106
],
},
"attributes": {"sex": face.sex, "age": face.age},
# TODO: face.embedding
}
for face in faces
],
},
}
検出結果で用意されているattributesがめちゃくちゃ優秀。
RAPiDは「Rotation-Aware People Detection in overhead fisheye images」の略 つまり「角度を意識した」人物検出、ということ
YOLOをベースにCOCOデータセットで学習をおこなった後に魚眼レンズにて追加学習を行い、その際に画像の中心とそこからの距離、角度の情報を加えています。 そうすることで自動的にその人物をバウンディングボックスで囲った時の角度まで推論できる その角度を推論するのも含めた損失関数を拡張(周期的損失関数)しているため、推論は一回で済み、YOLOと推論する速さはほぼ変わらない
魚眼レンズに対応したモデルがあることは知らなかった。
コードの商用利用が不可なのがつらみ
アーキテクチャー図
AWSでの構成図
機械学習モデルの学習ジョブ・モデル管理・バッチでの推論処理はAmazon SageMakerを用いて実装できます。 一方で、今回の様なバッチでの推論精度監視には、SageMaker Model Monitorを利用できないため、別途開発が必要 さらに、機械学習モデルの再学習についても、Amazon SageMakerの学習ジョブを起動する機能の開発が必要
今回は、バッチでの推論精度監視を、AWS Lambda、Amazon CloudWatch、Amazon SNSを利用して開発しました。また、精度劣化検知時の再学習機能を、AWS Step FunctionsとAWS Lambdaを利用して開発
Amazon SNSを通す必要はあるのだろうか? なんとかんCloudWatchからそのままLambdaを起動できそうだけども
3分で作る、CloudWatchイベントで実行するLambda
学習データが少ない状況下での方法論を整理しつつ、自己教師あり学習やFomura-driben Approachなどを手厚く紹介している。 全117pの大作。
自己教師あり学習はさまざまな手法の概要も簡単にまとめられているのでとても良い。
とてもありがたいチュートリアル資料。
一休.comのデータサイエンティストが書いたEDA: Easy Data Augmentation Techniques for Boosting Performance on Text Classification Tasksを日本語データに使ってみたブログ。
同義語に置き換える方法をWordNetからとChive(Word2vec)からの2通り試しています。
EDAの実装
# from https://user-first.ikyu.co.jp/entry/2021/07/27/155513
alpha = 0.3 # 単語を操作する割合
N_AUG = 16 # 一文から増やす文章の数(倍率)、500: 16, 2000: 8, 5000: 4
def synonym_select(target_token):
if target_token.part_of_speech()[0] == '動詞' or \
(target_token.part_of_speech()[0] == '形容詞' and target_token.part_of_speech()[1] == '一般'):
target_word = target_token.dictionary_form()
else:
target_word = target_token.surface()
synonyms = search_similar_words(target_word)
if len(synonyms) > 0:
replacement = random.choice(synonyms)
else:
# 同義語が無かったら置換しない
replacement = target_token.surface()
return replacement
# Synonym Replacement 文中の単語の内n個、同義語に置き換える
def synonym_replacement(text_tokens, text_split, text_length):
n = math.floor(alpha * text_length)
indexes = [i for i in range(text_length) if text_tokens[i].part_of_speech()[0] in ['名詞', '動詞', '形容詞']]
target_indexes = random.sample(indexes, min(n, len(indexes)))
for i in target_indexes:
target_token = text_tokens[i]
replacement = synonym_select(target_token)
text_split[i] = replacement
return text_split
# Random Insertion 文中の単語をランダムに選んで同義語にしてランダムな場所にinsert、n回繰り返す
def random_insertion(text_tokens, text_split, text_length):
n = math.floor(alpha * text_length)
indexes = [i for i in range(text_length) if text_tokens[i].part_of_speech()[0] in ['名詞', '動詞', '形容詞']]
target_indexes = random.sample(indexes, min(n, len(indexes)))
for i in target_indexes:
target_token = text_tokens[i]
replacement = synonym_select(target_token)
random_index = random.choice(range(text_length))
text_split.insert(random_index, replacement)
return text_split
# Random Swap 文中の二つを入れ替える n回繰り返す
def random_swap(text_split, text_length):
if text_length < 2:
return ''.join(text_split)
n = math.floor(alpha * text_length)
target_indexes = random.sample(range(text_length), 2)
for i in range(n):
swap = text_split[target_indexes[0]]
text_split[target_indexes[0]] = text_split[target_indexes[1]]
text_split[target_indexes[1]] = swap
return text_split
# Random Deletion 確率pでランダムにそれぞれの単語削除
p = alpha
def random_deletion(text_split, text_length):
return [t for t in text_split if random.random() > p]
# Easy Data Augumentation
def eda(text_tokens, text_split, text_length):
results = []
for _ in range(N_AUG):
text_tokens_c = copy.copy(text_tokens)
text_split_c = copy.copy(text_split)
random_number = random.random()
if random_number < 1/4:
result_arr = synonym_replacement(text_tokens_c, text_split_c, text_length)
elif random_number < 2/4:
result_arr = random_insertion(text_tokens_c, text_split_c, text_length)
elif random_number < 3/4:
result_arr = random_swap(text_split_c, text_length)
else:
result_arr = random_deletion(text_split_c, text_length)
results.append(''.join(result_arr))
return list(set(results))
WordNet ベースの置換
# from https://user-first.ikyu.co.jp/entry/2021/07/27/155513
conn_sqlite = sqlite3.connect("wnjpn.db")
re_alnum = re.compile(r'^[a-zA-Z0-9_]+$')
# 特定の単語を入力とした時に、類義語を検索する関数
def search_similar_words(word):
# 問い合わせしたい単語がWordnetに存在するか確認する
cur = conn_sqlite.execute("select wordid from word where lemma='%s'" % word)
word_id = 99999999 #temp
for row in cur:
word_id = row[0]
# Wordnetに存在する語であるかの判定
if word_id==99999999:
return []
# 入力された単語を含む概念を検索する
cur = conn_sqlite.execute("select synset from sense where wordid='%s'" % word_id)
synsets = []
for row in cur:
synsets.append(row[0])
words = []
for synset in synsets:
cur3 = conn_sqlite.execute("select wordid from sense where (synset='%s' and wordid!=%s)" % (synset,word_id))
for row3 in cur3:
cur3_1 = conn_sqlite.execute("select lemma from word where wordid=%s" % row3[0])
for row3_1 in cur3_1:
words.append(row3_1[0])
return list(set([w for w in words if not re.search(re_alnum, w)]))
Word2Vecベースの置換
vectors = gensim.models.KeyedVectors.load("chive-1.1-mc90-aunit.kv")
def search_similar_words(word):
thre = 0.6
try:
result = vectors.most_similar(word, topn=20)
return [r[0] for r in result if r[1] > thre]
except:
return []
生成例の比較 WordNet
お肉がとても美味しかったです。食後のコーヒーが別料金(210円)なので、そこだけ注意です。
=>
おミートがとても美味しかったです。食後のカフェーが画然たる勘定(210円型)なので、そこだけ注目です。
Word2Vec
お肉がとても美味しかったです。食後のコーヒーが別料金(210円)なので、そこだけ注意です。
=>
1. お胸肉がとても美味しかったです。空腹の水出しが各料(210¥)なので、そこだけ呉々です。
2. お肉がとても美味しかったコーヒーショップです。
¥食後のコーヒーが別料金(210円)な違う間食のでジューシー金額、細心ソーセージそこだけ注意です。
ブログでは、レストランの口コミから評価点(1~5)を予測するタスクをLSTMで実施。 DAをすればするほど、性能が上がる模様。
割と効果ありそうなので、使いたい。
類似語検索の部分は、BERTによる置き換えとかも追加しても良さそう。
以下の企業の決算から、AI企業の成長を促す3要素を紐解いている。
A.3つの成長ドライバー
・クロスセルや大口顧客増加による、1顧客あたり単価向上(WACUL、AI inside)
・顧客基盤の拡大(PKSHA Technology、ニューラルポケット)
・対象顧客の拡大(PKSHA Technology、ALBERT)
PAKSHA, ALBERTの今後の戦略が面白い。
PAKSHAの図はとても参考になる。
matplotlibをガチャガチャ描かなくても、データセットのグリッド表示が可能になる。
チュートリアルはこちら
大まかな使い方
# from https://github.com/karolzak/ipyplot/blob/master/notebooks/gear-images-examples.ipynb
images = glob.glob(datasets_dir + 'gear_images' + '/**/*.*')
images = [image.replace('\\', '/') for image in images]
labels = [image.split('/')[-2] for image in images]
ipyplot.plot_images(images, max_images=10, img_width=150)
めっちゃ便利そう
MediaPipeを扱う良いサンプルな気がする。
UCIのSMS Spam Collection Data Setを用いて、以下の手法を試したブログ
LIMEが一番直感に近かった模様。
CountVectorizer+回帰係数で可視化
最終CLSトークンのattentionの合計をとっている。
全体的に高く出てしまう模様。また、非スパム/スパム共通の色となる。
サンプリングしたテキスト列と予測をLIMEに渡して実装。 結構よい
全体的に高く出てしまう。
実装も参考になるとても良い記事。
事業のフェーズとしてはPMFして、拡大させていこうとするフェーズです。PMFしているからといって、プロダクトが完璧ということは全然なく、データ分析を駆使してプロダクトを改善しています。 その際に、特に次の2点が大切と感じており、順を追って説明します。 ・現場とデータの両面からの分析 ・データ分析がしやすい環境作り
データがあるとデータとにらめっこして示唆を出そうとしますが、現場に行って、定性情報を得ることでそもそもデータに現れないような課題を発見するのが重要です。 現場や営業からの声に触れることで、課題の解像度が上がり、データをどの切り口で分析すれば良いかが分かります。
一方で、データ→現場のパターンもあります。データから外れ値や解釈が難しい要素を抜き出します。そのデータが起きる原因を現場に行って確認すると、我々が想定していなかったプロダクトの使われ方をしていて、プロダクト改善につながったケースもあります。
この段階の事業フェーズでは、因果推論や多変量解析などの高度な手法は使わず、クロス集計のような単純な方法で明らかに課題がある箇所を特定することが多いです。 ただ、差分の差分法(DID)や回帰不連続デザイン(RDD)などの概念を知っていると、分析の切り口が増えて役立ちます。例えば、特定のセグメントで施策をしたときに、施策前にそれぞれのセグメントで平行なトレンドがあるのかを確認した上で、試作後の影響度合いを確認することを徹底しています。
データ分析をする際には、そこからどんなアクションに繋がるかを念頭に置くことも大切です。 実際にプロダクト改善に繋がる示唆というのは、そこまで多くありません。 プロダクトを改善するとその数値が変わりうるのか、プロダクトの変更コストはどれくらいで、それを変えたときのインパクトはどれくらいかを考えながら分析することが大事で、現場感とプロダクトに対する深い理解が求められます。
現場とデータ両方に気を配る必要がある。
ドメイン知識とはまさしくこのことかも。
ソフトウェア開発の代表的なタスク
- 機能開発: 事業上の直接的価値貢献になる開発
- 不具合修正: 既存機能における仕様とのズレを直す開発
- Overhead: 機能開発以外のMTGや、採用や評価といった事務作業などのシステムの価値向上につながらない営み
- Ops Engineering: 信頼性向上のための自動化やインフラの設定。一度行うと価値が蓄積する点が Toil とは異なる
- Toil: 繰り返され、自動化できるのに手動で行っており、対処療法的に発生し、長期的な価値がない作業。事業成長に比例した工数がかかる
Toil は放置しておくとどんどん増え続けるため、Ops Engineering の活動によってそれを抑制し続ける必要がある Overhead は組織の都合で決まるものなので、割合を抑えることができる。
理想的な時間配分
タスク間には以下の関係性がある
特に重要なのは
組織成長すると Overhead が増える Overhead には要件品質を向上したり技術力そのものを向上するトレーニングが含まれるので、部分的に開発品質向上に貢献する 機能開発は事業成長に貢献するが、開発品質という係数がかかる 開発品質が落ちると不具合修正工数が増える Ops Engineering によって Toil を抑えることができる
以下のようなケースが考えられる。
これは開発品質が低いことを意味するので、「要件を正確にするるためのMTGを増やす」「アーキテクチャーやテスト技法を習得するためのトレーニングを増やす」「Ops Engineering を増やす」ことで開発品質を向上させる必要がある
これは、急激な事業成長によって Ops Enginnering が不足していることが原因である。 Toil は事業成長によって減ることはないが、早めに Ops Engineering に割り当てることで撲滅していく必要がある
組織が大きくなるとナレッジを共有するためにどうしても同期的なコミュニケーションが必要になり、気づいたら「週の半分 MTG だった」ということになりかねない。 スクラムの定常イベント(朝会やリファインメントなど)は思った以上に全体の工数を圧迫する
一方、望ましい Overhead も存在する。それが「要件の精緻化」と「トレーニング」である。
要件があいまいなまま開発に着手し、あとから大きな手戻りが発生したことがある人は多い。
アーキテクチャの審美眼やテスト方法、 CI/CD の構築方法などは時間を割いてチームのナレッジとする価値がある。ここを疎かにすると近い将来属人化が進み、開発品質が上がらなくなる
織やシステムが必要とする人的リソースに対して、実際の頭数・スキルレベルが不足している。 短期的には業務委託でカバーし、中長期的には採用を行おう。
平社員だけどとてもためになる。
シミュレーションデータ x AIが来ている。。
今回、3DCGによる人体シミュレーションによって大量の学習データを作成し、それをPFNのスーパーコンピュータで学習して、全身を総合的に認識できる高度な3D姿勢推定モデルを構築。専用カメラによる撮影や、身体へのセンサー装着の必要がなく、これまでの技術で課題となっていた指先の向きや両手が重なる場面などでの誤検出を大幅に削減し、 スマートフォン等で撮影した動画でも身体細部の動きを高精度にトラッキングできるようになりました。
モデリングスキル結構大事になりそう。
[元記事]()
山形大学の片平光彦教授と堀口健一教授、ViAR&Eの市浦茂社長は深層学習を使った鶏の行動判定技術の開発に注力する。 4000枚の画像を学習させることで採餌と水飲み、休憩の識別率が100%になった
食肉用のブロイラーは平飼いが主流。平飼いなら天井に設置したカメラ1台で鶏100羽以上の行動データを集められる。
同時に羽紋で1羽ごとに個体識別して追跡する技術も開発中。 1羽ごとに体重が増える速度を記録して活動量を可視化する。 鶏は別の鶏をつつき羽根をむしるなど厳しい序列をつくる習性がある。そのため、集団の中でいじめられ弱っている固体を特定できれば、区画を入れ替えるなど対応ができる
鹿児島大学の小沢真准教授は、富士通鹿児島インフォネットや中嶋製作所などと共同でカメラ映像から鶏の体重や活動量を推定する技術を開発した。 画像認識AIで鶏を識別し、画像の鶏の大きさから立体的な体積を求め、体重を算出する。推定誤差は調整前でプラスマイナス5%
活動量の計測では鶏を識別して数秒後の画像でどれだけ移動したかを計算する。鶏が風邪をひいて活動量が下がるなど病気で死ぬ予兆を探す。日々の変化に対し、急に活動量が減ると何か異常が起きているというサインにもなる。
意外と平飼いの鶏に対するプロダクとが多くて驚いた。
鳥の識別ってどうやってるんだろう...?羽紋ってのがあるみたいなので、それを使えば指紋みたくできる感じ..?
公式レポジトリの表が意外と使える。
物によっては10倍程度早くなるものもあるのが驚き。 ただし、物体検出系は早くなりづらいんだとか。
__slots__
を用いることで、クラスのメモリ使用率を削減できる。slots を使うと、(プロパティのように) データメンバを明示的に宣言し、 (明示的に slots で宣言しているか親クラスに存在しているかでない限り) dict や weakref を作成しないようにできます。 dict を使うのに比べて、節約できるメモリ空間はかなり大きいです。 属性探索のスピードもかなり向上できます。
slotsにはいくつか注意点があるようだ。
- slots を持たないクラスから継承するとき、インスタンスの dict 属性と weakref 属性は常に利用可能
- dict 変数がない場合、 slots に列挙されていない新たな変数をインスタンスに代入することはできません。新たな変数を動的に代入したいのなら、 slots を宣言する際に 'dict' を変数名のシーケンスに追加してください。
- slots は、クラスのレベルで各変数に対するデスクリプタ (デスクリプタ (descriptor) の実装 を参照) を使って実装されます。その結果、 slots に定義されているインスタンス変数のデフォルト値はクラス属性を使って設定できなくなっています; そうしないと、デスクリプタによる代入をクラス属性が上書きしてしまうからです。
- あるクラスで、基底クラスですでに定義されているスロットを定義した場合、基底クラスのスロットで定義されているインスタンス変数は (デスクリプタを基底クラスから直接取得しない限り) アクセスできなくなります。これにより、プログラムの趣意が不定になってしまいます。将来は、この問題を避けるために何らかのチェックが追加されるかもしれません
実際どれくらいのメモリ節約ができるのだろうか。
class Point(object):
def __init__(self):
self.x = 0
self.y = 0
print(sys.getsizeof(Point))
>>> 1056
point = Point()
print(sys.getsizeof(point))
> 56
class Point(object):
__slots__ = ['x', 'y']
def __init__(self):
self.x = 0
self.y = 0
print(sys.getsizeof(Point))
>>> 888
point = Point()
print(sys.getsizeof(point))
> 56
どうもインスタンスのメモリは減らないが、classの方のメモリ使用量が減る模様。
減るっちゃ減るけど、ここまでメモリを減らさなくては行けない場面ってそこまでないのかも。
Google Researchは、ByT5をオープンソース化している。これは抽象的なトークンの代わりに未加工のバイトで動作するモデルである。ベースラインモデルと比較して、ByT5はいくつかのベンチマークタスクでより正確であり、スペルミスやノイズに対してより堅牢である。
バイトレベルの処理では、ベースラインと比較して推論時間が遅くなりますが、ByT5はmT5よりもノイズに対してはるかに堅牢である。経験として、ランダムに大文字や小文字を変更したテキストが与えられた場合、mT5の25%と比較して1%の精度低下で済んでいる。ByT5は、生成タスクおよびXTREME多言語NLPベンチマークでもmT5よりも優れている。
バイトレベルモデルの欠点の1つは、モデルの後続のレイヤーに供給される結果のシーケンスがトークン化されたものよりもはるかに長く、その結果、モデルが大きくなり、遅くなることである。
ByT5を実装するために、研究者は3つの方法でmT5アーキテクチャを変更した。
- UTF-8バイトがモデルに直接提供される。ただし、UTF-8で無効なバイトはすべて削除され、パディングと文の終わりを表すために2つの特別なトークンが使われる。
- トレーニング前のスパン破損タスクが変更され、平均3トークンをマスクするmT5と比較して、平均20バイトがマスクされる。
- 最後に、エンコーダーとデコーダーに同じ数のTransformerブロックを使うのではなく、ByT5ではエンコーダーの深さはデコーダーの3倍となる。
byT5はSuperGLUE(言語理解)やXSumとTweetQA(生成タスク)、XTREMEなどのタスクでmT5よりも性能が高かったものの、その他のタスクではまちまちだった。
ByT5は低速で、事前トレーニングを完了するのに33%長いクロック時間がかかり、推論時間は分類で最大2倍、生成で最大7倍遅かった。
CHNINEとの根本的な違いはなんだろうと思って調べてみたら、こう描かれていた。
though the “CANINE-S” model still uses a tokenizer during pre-training to define targets for the masked language modeling task. (a) we train encoder-decoder models that extend to generative tasks, (b) our models work directly with UTF-8 bytes (c) we explore the effect of model scale, training models beyond 10 billion parameters.
文字を画像にした後にConvolutional AEで再構成させることで、文字の図形的な埋め込み表現を獲得する。
フォントが図形として描写可能なすべての文字に対して、背景が黒色で文字が白色の60x60の画像を作成しました。学習の際には、画像をグレースケールに変換後に正規化しました。
埋め込み表現の利用はgensimが使える。
from gensim.models import KeyedVectors
model = KeyedVectors.load_word2vec_format("data/convolutional_AE_300.bin", binary=True)
In []: model.most_similar("油")
Out[]:
[('汕', 0.9025427103042603),
('泊', 0.8892871737480164),
('伷', 0.884428083896637),
('浊', 0.8678311109542847),
('沖', 0.8532482385635376),
('沽', 0.8451510667800903),
('沺', 0.8355003595352173),
('沾', 0.8313066959381104),
('涃', 0.8284391164779663),
('泩', 0.8275920152664185)]
かなり面白い試み。
誤字に強くなりそう。
AEをVAEにするのも良いかもしれない。
Twitterが、システムが自動的に画像をクロップする際の”偏り”を発見した人に謝礼を支払う報奨金コンテストを開始しました。
Twiiterの自動画像クロップは2018年から使われ始めましたが、一部ユーザーからはこのアルゴリズムが肌の白い人を中心にするようなバイアスがかった処理を行う傾向があると批判の声が上がっていました。
この報奨金コンテストは「業界初」のアルゴリズムのバイアスを対象とした報奨金プログラム
機械学習のバイアスを探すコンペティションはかなり面白い試み。
社会的な問題として批判されるよりも、ユーザーに事前に発見してもらえるほうが企業的には利があるのだろう。
報奨金は最高3500ドルであるので、実際どの程度の人が参加するかが今後の資金石となるだろう。
気になったものを抜粋。
NG: 1日以上かかりそうなタスクの分解をしない → 時間がかかりそうなタスクは2、3時間で終わる単位に分割しよう
NG: 技術調査をするときに、メモを取らない → 調べる際に参考にしたサイトのURLをメモしておくと、時間を溶かすことなく調査が進むだろう
NG: 他人と比較する → そもそも近年のプログラミングはかなり多岐に渡るのでわからないことは無限にある。 比較をすること自体がナンセンスだ ある程度のレベルまでいくと比較はあまり意味をなさない。
NG: 複数の機能開発を同時に行う → コードを書く際は一定の時間を確保しましょう
肝に銘じていきたい。
開発資料 とTogetter がまとめられている。
気になったのは以下。
【18-C-1】「スピード」と「品質」のスイッチング ~事業成長を支える生存戦略~(城戸 総史[メルペイ]/長谷川 亮[メルペイ]/横山 翔)
別の資料まとめもああった。
時間ある時にじっくり読みたい。
[元記事]()
Horaという高速なベクトル検索ライブラリを用いた顔認識システムの構築例
特徴は以下
依存関係が少なく、さまざまなOSやモバイル端末で使用可能。 SIMD命令を利用しているため高速な模様。
ベクトル検索ライブラリいろいろ出てきてる。
こいつは速度のわりに、recallが高い。
気になったものだけ抜粋
git checkout . ステージングされていない修正を取り消す。
よく用いられるコマンドが列挙されているので復習に良い。
マルチプロセスとは プロセスとは実行中のプログラムです。 1つのプロセスは、OSから空いているCPUコアが割り当てられることにより、処理を進めることができます。 マルチプロセスとは、複数のプロセスが同時に処理を進めることを指します。マルチプロセスのメリットは、1つのプログラムの目的を達成するために複数のCPUのコアを利用することで、より速く目的を達成できるという点
マルチスレッドとは スレッドとは、プロセスの中における処理の流れのことです。 1つのスレッドは、プログラミング言語毎に実装されている機構(LinuxではPthread、JavaのThreadsライブラリ、Pythonではやthreadingライブラリ等)を通してCPUコアが割り当てられることにより、処理を進める プロセスのように、OSから直接CPUコアが割り当てられるのではありません。 プロセスの場合と同様に、CPUのコアが複数ある場合、それぞれのコアを複数のスレッドに対して同時に割り当てることができれば、複数のスレッドの処理を同時に進めることができます。
ここでいうスレッドとは、
print('Hello')、print('world')、print('!')、そしてメインスレッドの4つの処理のことで、job.join()関数の実行後はスレッドが完了します。 print('done')が実行される時点においては、スレッドはメインスレッドの1つだけです。
# from https://tech.jxpress.net/entry/2021/07/29/101150
import threading
jobs = [] jobs.append(threading.Thread(target=lambda : print('Hello'))) jobs.append(threading.Thread(target=lambda : print('world'))) jobs.append(threading.Thread(target=lambda : print('!')))
for job in jobs: job.start() for job in jobs: job.join()
print('done')
> Pythonにおけるマルチスレッド
> Pythonにおいて、マルチスレッドなソースコードを書く場合、CPythonがGILがあることを考慮しなければなりません。
> GILであるインタプリターにおいては、マルチスレッドなソースコードを書いたとしても、インタプリターが出力したバイトコードをOS上で実行する段階においてマルチスレッドでは実行されません。
### 比較実験 ①
> CPU負荷の高い処理(いわゆるCPU bound)を達成するためのソースコードである場合、multiprocessingを利用し、マルチプロセスに書きましょう
> CPU負荷の高い処理するためにマルチスレッドなソースコードを書いたとしても、パフォーマンスは改善されません。なぜなら、「Pythonにおけるマルチスレッド」で説明した通り、Pythonのソースコードはインタプリターによりコンパイルされた後、OS上でシングルスレッドで実行されるからです。
<img width="500" alt="スクリーンショット 2021-08-02 13 01 28" src="https://user-images.githubusercontent.com/19774756/127802750-8a468151-92c6-4f34-a41d-707e3c9d7050.png">
### 比較実験②
> I/O待ち時間が大きいもの(いわゆるI/O bound)を達成するためのソースコードである場合、threading(マルチスレッド)かasyncio(非同期I/O)を利用しましょう。
> multiprocessing(マルチプロセス)を利用しない方が良い理由は、プロセスを作る際に発生するコストが大きいから
> プロセスを作るコストよりもスレッドを作るコストの方が小さいので、コストが小さい方を利用した方が良い
> プロセスを新しく作ると、新しく作られたプロセスの数に比例してファイルディスクリプタ数、OSがCPUを切り替えるためのスイッチング回数が大きくなります
> スレッドを作るコストという観点から言えば、スレッドを作るコストよりも非同期I/Oのイベントを発火するコストの方が小さいため、asyncioを利用する方が良い
<img width="400" alt="スクリーンショット 2021-08-02 13 07 16" src="https://user-images.githubusercontent.com/19774756/127803096-4b61ba52-88ed-4b9f-ab0a-87a27b0203bd.png"><img width="400" alt="スクリーンショット 2021-08-02 13 07 42" src="https://user-images.githubusercontent.com/19774756/127803134-690f9b78-9864-4c96-82c3-92d877fd0e63.png">
ここからわかることは
> (1)過度なタスク分割によるオーバーヘッド増大
> スレッドやイベントループ、その他諸々のオーバーヘッドの影響が大きくなってしまったことが起因していると考えられます。
> タスクを小さくすればするほどそれぞれのスレッドは速く終了しますが、よりたくさんのスレッドを生成・管理しなければなりません
> (2)OSのスレッド数上限値が影響
> 1プロセス毎に作ることのできるスレッド数には上限値があります。CPythonのスレッドはpthreadを用いて実装されているため、この上限値の影響を受けます。
> (3)パフォーマンス頭打ち
> 理想的なパフォーマンスの向上が頭打ちになっている状態です。
> (4)タスク分割数に比例してパフォーマンス向上
> 単タスクの量と処理時間がほぼ同じです。マルチスレッド、非同期I/O、共に、理想的なパフォーマンスの向上が実現できています。
> io_threading.pyとio_asyncio.pyの処理時間に差異がほとんどありません。これは(1)で述べたようなオーバーヘッドの影響が無視できるほど小さいからだと思われます。
### コメント
pythonでの並列処理はややこしく、いまいち理解ができていなかったので、とても勉強になった。
### 出典
[元記事](https://tech.jxpress.net/entry/2021/07/29/101150)
Faissのチュートリアルがjupyter notebook 形式でまとめられている。 スピードと精度の兼ね合いや、quantization、ベクトルの復元などの方法についての言及もある。
表題の通り。
ja-timex は、現代日本語で書かれた自然文に含まれる時間情報表現を抽出しTIMEX3と呼ばれるアノテーション仕様に変換することで、プログラムが利用できるような形に規格化するルールベースの解析機です。
以下の機能を持っています。
- ルールベースによる日本語テキストからの日付や時刻、期間や頻度といった時間情報表現を抽出
- アラビア数字/漢数字、西暦/和暦などの多彩なフォーマットに対応
- 時間表現のdatetime/timedelta形式への変換サポート
入出力例
# from https://github.com/yagays/ja-timex/
from ja_timex import TimexParser
timexes = TimexParser().parse("彼は2008年4月から週に3回ジョギングを1時間行ってきた")
[<TIMEX3 tid="t0" type="DATE" value="2008-04-XX" text="2008年4月">,
<TIMEX3 tid="t1" type="SET" value="P1W" freq="3X" text="週に3回">,
<TIMEX3 tid="t2" type="DURATION" value="PT1H" text="1時間">]
datetimeやtimedeltaなどにも変換可能らしい
めっちゃ便利そう
Googleが20億パラメータのAIビジョンモデルをトレーニング
またImageNetのSoTaが更新された。
このモデルに関しては学習済みモデルの公開はないと、開発者が公言している。
コメント
進歩が早いなぁ。
そろそろImagenetでのベンチマークも意味を失いつつあると思うが...
出典
元記事