このページの内容が正しいとは限りません。なるべくミスらないよう、がんばるけど。過去の記事もまちがい等に気がついた時点で書き換えていきます。図版の一部は外部へのリンクなので、その図版サーバが落ちていたらゴメンナサイ。
検索エンジンで調べてたどり着いた人へ:上の「検索」で日記内の検索をかけてみるか、記事一覧を見てください。書いて欲しい項目のリクエストがあれば、コメント欄に書いて下さい(ただし高校数学程度の範囲内でね)。なるべく答えてみようと思います。


あらきけいすけの研究日誌の別館のようなものになってしまった。mimeTeXが使えるので使っている。高等学校数学に関するメモを書き留めるつもりで始めた(新しい記事も過去の日付に追加して書いている)。

2008.5.9:いくつかのリファラを消すつもりで、エントリ全体を誤ってバッサリと消してしまった。トラバも意に反して消してしまった。検索エンジンのキャッシュを元にリンクさせていただきます。
http://d.hatena.ne.jp/muffdiving/20071115/1195141546
あらき氏が「匿名のつもり」だったはずはないことを明示しとく - 石田のヲモツタコト

Raspberry Pi 3 の SPI を用いてA/Dコンバーターからデータを読む python 関数 readadc() の各行の動作

教育用の覚え書き。ラズパイ3で標準のSPIバス(+RPi.GPIOライブラリ)を用いてA/DコンバーターICからセンサ値を読み出す解説記事に頻出する python 関数 readadc() の各行の動作を確認したのでメモを残す。output()でbit1個分のピンへのON/OFF信号の送出, input()でbit1個分のデータ読み出しを実行しているので、呼び出し時の関数の動作時間は多分、一定していない。コメントはA/DコンバーターとしてMCP3208を想定して書いている。

def readadc(adcnum, clockpin, mosipin, misopin, cspin):
# 宣言しておく import 文
# import RPi.GPIO as GPIO
# 入力(すべてint型)
# adcnum: データを読み出すMCP3208のチャネル番号 0, ..., 7
# clockpin: クロック(CLK)信号を出力するラズパイのピン番号
# misopin: Master In Slave Out のラズパイのピン番号
# mosipin: Master Out Slave In のラズパイのピン番号
# cspin: Channel Selector のラズパイのピン番号
# 戻り値
# int 型, 0, 1, 2, ..., 4095: adcnum チャネルのA/D変換値
# -1: adcnum が 0, ..., 7 の範囲にない

# 読み出しチャンネル番号が 0, ..., 7 に無ければ処理しない
if adcnum > 7 or adcnum < 0:
return -1

# CLK への出力を0に初期化しておく
# この関数では CLK のパルス生成を GPIO.output(*,1),
# GPIO.output(*,0) の連続呼出で実行している
# CLKパルスの立ち下がりのタイミングで1bitの入出力が起こる
#
GPIO.output(cspin, GPIO.HIGH) # I/Oが起きないようにCSを1にする
GPIO.output(clockpin, GPIO.LOW) # CLK を0に設定しておく
GPIO.output(cspin, GPIO.LOW) # I/Oを始めるためにCSを0にする

# この3行は commandout に MSB IN のデータ(8bitで上位5bitがデータ)を
# 作成する部分(秋月の MCP3204/3208 のPDFの p.20, Fig. 5-1.)
#
# タイミングチャートの3行目の D_IN に書いてある
#
# [Start][SGL/DIFF][D2][D1][D0]
# | | | | |
# | | 読み出しチャンネルの指定
# | 0:差動入力
# | 1:シングル・エンド
# 1:スタートビット
#
# を作成する
commandout = adcnum # [ 0][ 0][ 0][ 0][ 0][D2][D1][D0] adcnum
commandout |= 0x18 # [ 0][ 0][ 0][ 1][ 1][D2][D1][D0] 0x18と論理和
commandout <<= 3 # [ 1][ 1][D2][D1][D0][ 0][ 0][ 0] 3bitシフト

# このループは作成した commandout の上位5bitを1bitずつ送り込むループ
for i in range(5):

# commandout の最上位1bitが1ならば、MOSIに1を送り込み、
# さもなければ、MOSIに0を送り込む
if commandout & 0x80:
GPIO.output(mosipin, GPIO.HIGH)
else:
GPIO.output(mosipin, GPIO.LOW)

# MOSIに送り込んだら commandout の内容を1bitずらす
commandout <<= 1

# CLKに1パルス送り込む
GPIO.output(clockpin, GPIO.HIGH)
GPIO.output(clockpin, GPIO.LOW)

# 出力データ adcout を1bitずつ読み込むループ
adcout = 0 # データ保存変数 adcout の初期化
for i in range(13): # 全部で 13 bit 読み込む

# A/Dコンバーターの CLK に1パルス送り込む
GPIO.output(clockpin, GPIO.HIGH)
GPIO.output(clockpin, GPIO.LOW)

# adcoutを1bit左にずらして、最下位bitに空きを作る
adcout <<= 1

# もし MISO に1が入っていたら、adcout の最下位bitに1を書き込む
if i>0 and GPIO.input(misopin)==GPIO.HIGH:
adcout |= 0x1

# データ通信が終わったら CS をHIGHにして通信を止める
GPIO.output(cspin, GPIO.HIGH)

# 読み出しデータを呼び出し側に戻す
return adcout

複数のGPIOピンからのpwm信号出力が欲しいがゆえにpigpioライブラリをインストールしたが、ライブラリ中のSPIの関数pigpio.spi_*()たちの引数の与え方が分からずに、このコードをpigpio.read()/write()を使って書き換えた関数を使ってセンサ値を読み出しているのは内緒。

[2018.10.29追記] pigpio の spi_open(), spi_xfer() の用法が分かった:pigpio ライブラリの spi_xfer() 関数を用いて Raspberry Pi 3B から SPI 接続のA/Dコンバータ MCP3208 を利用する - あらきけいすけのメモ帳

3行で語るlim(1+1/N)^N(ここでは自然数)の由来

授業のための覚書
ネイピア数eの定義がなぜあの形か,先生は説明をしてくれなかった | ロボット・IT雑食日記
学習したことを内省して概念化して理解を深めていくプロセスってこんな感じだよなあ。てゆーか、ボク自身も受験勉強の最中(とそれ以降)は無自覚、無批判に

指数法則a^{x+y}=a^xa^y, a^{xy}=(a^x)^yが任意の実数 x, y で成り立つ
ことを受け入れて式変形にいそしんでいた。
それって社畜ならぬ数畜?
具体的に「0.5回の掛け算」って実行できる?「0.5回の掛け算」は「平方根」で平方根は「開平計算*1」や「バビロニアアルゴリズム*2」で値を求めることができて…という風に、「同じ値を与える(とせんせーがゆっていた)別の方法」に焼き直して計算していない?先生に言われるままに\sqrt{2}=1.4142...を受け入れてなかった?

eの定義と万能の指数

ボクはここ数年の数学の授業では次の話を振ることにしている:

\underbrace{(1.001)\times(1.001)\times\cdots\times(1.001)}_{694times}=2.001...\approx2 だから  \underbrace{(1.001)\times(1.001)\times\cdots\times(1.001)}_{347times}=1.414...\approx\sqrt{2} じゃね?
この計算って1.1, 1.01, 1.001, 1.0001, ..., 1.00...001って細かくしたら、どんどん値が正確になるし、x=(1.00...01)^N で1より大きいどんな数でも作れるから、究極の「n乗根計算表」って作れね?*3
例えば\sqrt{2}
\sqrt{2}\approx(1.1)^{3}\approx(1.01)^{34}\approx(1.001)^{346}\approx(1.0001)^{3465}\approx...
ただこれでは指数の桁が膨大になるので、指数に小数もOKという風に指数のかけ算ルールの定義a^{xy}=(a^x)^yを拡大して
\sqrt{2}\approx((1.1)^{10})^{0.3}\approx((1.01)^{100})^{0.34}\approx((1.001)^{1000})^{0.346}\approx((1.0001)^{10000})^{0.3465}\approx...
となる。ここで出てきたのがネイピア数 e
(1.1)^{10},(1.01)^{100}, (1.001)^{1000}, (1.0001)^{10000}, ..., \displaystyle e:=\lim_{N\to\infty}(1+\frac{1}{N})^N=2.718...
くそまじめな整数回の掛け算が考え方の基本になっているので、これは値を求める計算のアルゴリズムが明快。逆にいくつかの参考書で見かける定義 \displaystyle e:=\lim_{x\to0}(1+x)^{\frac{1}{x}} は直接のアルゴリズムで書けない「実数回の掛け算」がコッソリと導入されているので、いただけない。

ついでにeの定義を使わずにロジックだけで対数関数、指数関数の導関数を求める

高校までの微分積分の知識(合成関数、逆関数導関数微分積分が逆演算)が一通りあるなら、こんな導出もある;

  1. 対数関数は f(xy)=f(x)+f(y)…(1) を満たす微分可能な関数。
  2. (1)に x=1 を代入すると f(1)=0 とわかる。
  3. (1)に x=0 を代入すると f(y)=0 になっちゃうのでf(0)は定義できない。
  4. (1)をy微分すると、x\,f'(xy)=f'(y) なので、これにy=1を代入すると f'(x)=f'(1)x^{-1}
  5. だから対数関数は \displaystyle f(x)=f'(1)\int_1^x\frac{dx}{x} である。つまり  \displaystyle y=\frac{1}{x} のグラフを描いて面積を求めれば対数の値が求まることがわかる。*4
  6. ついでに対数関数は f'(x)=f'(1)x^{-1} なので、対数関数の逆関数gとする)の導関数逆関数導関数の公式より g'(x)=g(x)/f'(1) となる。というわけで指数関数(対数関数の逆関数)の導関数の公式が求められる。

*1:開平法 - Wikipedia

*2:Methods of computing square roots - Wikipedia 日本語のWikipediaには載っていない。

*3:ネイピア数 - Wikipediaの「歴史」「定義」の項のベルヌーイの利子計算の話を参照。

*4:f'(1)の値は対数関数の底をaとするとき、f(a)=1からf'(1)=1/\log_eaを導出できる。ここで\displaystyle\log_ex:=\int_1^x\frac{dt}{t}とする。

else if はC言語の仕様には存在しない

授業のための自分用の覚書。Cの文法の仕様*1には if ... else if ... という文法事項は書かれていない。

if ( [expression] ) [statement] else [statement]
しか明記されていない。ついでに言うとコードを書くときのお作法の波括弧*2も無い。else if が使える理由は if ( [expression] ) [statement] else [statement] の全体が一つの [statement] であるので、else の後の [statement] に代入できてしまうのである。制御文のコーディングの標準のお作法からするとチートな書法である。

if        ( A ) {
} else if ( B ) {
} else if ( C ) {
} else {
}

*1:PDF資料:http://www.open-std.org/jtc1/sc22/wg14/www/docs/n1124.pdf の 6.8.4 Selection statements

*2:例えば IPA 組込みソフトウェア開発向けコーディング作法ガイド[C言語版] http://www.ipa.go.jp/files/000005123.pdf の p.75

インデントを崩さずにWordにソースコードを貼る方法

いくつかのサイトを見て共通するノウハウをメモする

  1. ソースコードを1行1列の表の中に書き込む
    [目的]Wordの自動修正機能をキャンセルできてしまう
  2. MSゴシックフォントを利用する
    [目的]等幅フォントでインデントを揃える
  3. 「段落」機能で「行間」をフォントサイズ+1の「固定値」にしてしまう
    [目的]1ページに入る行数を固定化してしまう
  4. 「タブ」はなるべく「半角スペース」に置き換える
    [目的]インデントの型崩れを避ける

グループ学習授業に「フリーライダー」っているのかな?

教育用の覚書。以下に日頃の授業を見ていて感じる「藁人形」を記す。
グループ学習の授業の「フリーライダー」という表現を聞くと、最近のウェブ上の(発言者は少ないのだろうが)やたらに目立つ障がい者や透析患者や生活保護受給者への侮蔑的な言説と似た、「役立たず(カッコつき)」への差別に似たにおいを感じてしまう。グループの中でグループの活動に関与(commit)できない、グループの目標に寄与(contribute)できないという「活動、目標から疎外された(alienated)状態」が問題なのではないか?
つまり「(意識的に)コミットしない(すなわちサボる)」のではなく、「コミットの方法、切り口、ロールモデルを知らないので行動ができない」のではないだろうか?*1参加のモチベーションよりむしろ参加者のロールモデル*2を内部に持たない人なのではないか。
では commitment/contribution を妨げる/促す心理は何かと言えば、参加した場に対して

「懸念・疑問・アイデア・ミスなどを声に出しても大丈夫だ」という信頼があるかどうかで決まります。*3
これは Amy Edmondson が「心理的安全性(psychological safety)」*4としてまとめたものである。これと同じ趣旨の記事としては Google のプロジェクト・アリストテレス*5を紹介したいくつかの記事がある(これも Edmondson の心理的安全性の活用例である)。この「心理的安全性」の醸成ができれば「フリーライダー」が減るのではないだろうか?
「参加者」の具体的な行動のモデルとしては、パズルを解くような研修プログラムのやり方がひとつの範例となるかもしれないが、設計、準備が大変。心理的安全性の確保とその上でのロールモデルの提示と行動の促しというのはとてもチャレンジング*6
ちょっとズルいかもしれないが、「ロールモデルを知っていたら、ポジティブな演技をして、埋没できるよ」と説得するのもありかもwwwww

*1:もちろん全員がフルにコミットした状態というのも、ファシズム的でキモチワルイ状態だと思ってしまう。

*2:わたし自身が「参加者」「ファシリテータ」のロールモデルでいくつかの研修を形式的にしのいだことがあるwwwwwwもちろんロールモデルと思考のトレーニングになったwwwww

*3:職場を崩壊させないために必要な「心理的安全性」を作り出す方法 - GIGAZINE
http://gigazine.net/news/20161020-psychologically-safe-workplace/
これはTED講演の紹介記事
Building a psychologically safe workplace | Amy Edmondson | TEDxHGSE - YouTube
https://www.youtube.com/watch?v=LhoLuui9gX8

*4:amy edmondson 1999 Psychological Safety and Learning Behavior in Work Teams - Google 検索

*5:おそらくこれの1次文献的記事はNYTのWhat Google Learned From Its Quest to Build the Perfect Team, New research reveals surprising truths about why some work groups thrive and others falter. By CHARLES DUHIGG で、日本語の記事でプロジェクト・アリストテレスの出典を書いたものは完璧なチームはどうやって生み出されるのか? - GIGAZINEくらいである。

*6:チャレンジング:とても難しそうのポジティブな言い換え