12月第4週の振り返り

12月第4週(12/23-12/29)

年の暮れにあまり目にしたい話題ではないと思うので法医学は折りたたんである。

並列プログラミング

汎用的なLU分解をするにあたってはピボット=対角要素の適切な選択が必要となることは前回のコードの中で示したが、本来LU分解は一回きりのAx=bを満たすxを求めるのではなく任意の b_{i}に対応する解ベクトルx_{i}を効率よく求めるためのものである。そのため一度分解した後はピボット選択の結果を置換行列(permutation matrix)Pとして保持しておき、次からは左から掛けて PAx=Pb\\ LUx=Pb\\ Lc=Pb\\ Ux=cとしてbの行を入れ替えておかなければならない。 \begin{pmatrix}1&0&0\\0&0&1\\0&1&0\end{pmatrix}\begin{pmatrix}b_{1}\\b_{2}\\b_{3}\end{pmatrix}=\begin{pmatrix}b_{1}\\b_{3}\\b_{2}\end{pmatrix}といった演算が本当だが、積を求めるのは明らかに不要だし、置換行列は各行に非零要素を1つしか持たない疎行列なのでメモリも無駄である。「置換前の行列の各行は置換の結果どの行に行けばいいのか」を行数分保持した一次元配列としておけば足りるように思う(結果的に、疎行列の座標リスト=Coordinate方式になる)。

法医学
クリックで展開

医師法では妊娠12週以上の死産児を検案し異常があると認めたときは所轄警察署に届け出なければならないと定められている。胎児の殺害=堕胎罪となりうる可能性もあるため12週未満であっても届け出るのが無難である。

(嬰児が医療行為の介在があっても未だ生育可能でない)妊娠22週未満の時期に母体保護法に基づき母体保護指定医が行う人工妊娠中絶に関しては、堕胎罪にあたらない。

法医診断にあたっては生活能力の有無(流産・堕胎・殺人の判断材料)が重要となる。妊娠週数に応じた身長・体重・胎盤重量の計算式にあてはめて推定する。また呼吸開始により現れる所見(肺の辺縁が丸みを帯びる・泡沫の漏出・肺浮揚)を確認して生産か死産かを判断する。

予期せず分娩が起きることを墜落分娩と呼び、生産児であれば窒息ないし頭部外傷が主要な死因である。

0歳児の事故死のほとんどは窒息であり、行動範囲が広がる1~4歳では交通事故・溺水が多くを占める。

腋窩、側胸部、上腕・大腿内側などの損傷は転倒によって生じることは少なく、他為が疑われる。特異性が極めて高いのが二重条痕である。

乳児の頭部が揺らされる・つかまり立ち中の転倒などにより頭蓋内出血と眼底出血が生じ、昏睡・呼吸不全・死亡に至ることがある。

今年を終えるにあたって

やや短いながらも、これが2019年最後の復習記事となる。来年も精進していきたい。

12月第3週の振り返り

12月第3週(12/16-12/22)

債権総論

共同抵当とは、その語感とは異なり複数の債権者が抵当権を共有することではなく、同一の債権を担保するために複数の不動産に抵当権を設定することである。抵当権が実行された場合に後順位抵当権者の扱いを確定させるため、不動産間で負担の調整をする必要がある。

並列プログラミング

LU分解の過程において用いられるAの要素は求めようとするLまたはUの要素と同じ位置にある。そのためAの二次元配列とLUを組み合わせた二次元配列とを別々に持つ必要がないことが分かる(LまたはUの要素を求めたら、その位置にあるAの要素はもはや参照されることがないのでLまたはUで上書きしても支障がない)。これにより大規模な行列に対してメモリ使用量を削減することができる。

逐次計算によるLU分解は以下のようになる。素朴な実装ならLとUの配列をAとは別に確保しているところだが、省メモリ実装ではAを書き換えていくので、流れを追いやすいようプリプロセッサディレクティブを使ってL, Uと書けるようにした。

#include <stdio.h>
#include <math.h>
#define L A
#define U A
#define N 4

int main(void) {
    double A[N][N] = {
         0,  1,  4, -6,
         8,  1,  6, -2,
        -2,  0,  0,  3,
         4, -2, -2,  4
    };
    double b[N] = {-1, 13, 1, 4};
    
    double x[N];
    double c[N];

    // LU分解
    for (int k=0; k<N; k++) {
        // 部分ピボット選択
        // ピボットとする予定のU[k][k]が0だったり、小さかったりすると正しく計算できないので
        // 未処理部分の中で同列要素の絶対値が最大である行を探して入れ替える。対応するbも入れ替える
        // Aは途中までLとUに書き換えられているが、Lの未完成行は入れ替え可能なので行の全要素を入れ替えてよい
        double current_largest_abs = 0;
        int swap_row_idx;
        for(int i=k; i<N; i++){
            double candidate_abs = fabs(A[i][k]);
            if(current_largest_abs < candidate_abs){
                current_largest_abs = candidate_abs;
                swap_row_idx = i;
            }
        }
        // A swap
        for(int j=0; j<N; j++){
            double tmp = A[k][j];
            A[k][j] = A[swap_row_idx][j];
            A[swap_row_idx][j] = tmp;
        }
        // b swap
        double tmp = b[k];
        b[k] = b[swap_row_idx];
        b[swap_row_idx] = tmp;

        double pivot = A[k][k];
        double mult_inv = 1.0 / pivot; // 繰り返し除算をするのは遅いため逆数をとる

        // L 第k列(0-based index)
        for (int i=k+1; i<N; i++) {
            L[i][k] = A[i][k] * mult_inv;
        }


        // k+1行から最後の行までの全てにおいて
        // いつかは外側要素であるL[i][k]*U[k][j]を減算することになるので今のうちに行う
        for (int i=k+1; i<N; i++) {
            double Lik = L[i][k];
            
            // k+1列から最後の列までの全てにおいて減算する
            for (int j=k+1; j<N; j++) {
                U[i][j] = A[i][j] - Lik * U[k][j];
                // U 第k+1行(0-based index)はこれで求まる
                // それより下の行はまだ引くべき積が残っている
            }
        }
    }

    // Lc=bの上から順にcを求める
    for(int k=0; k<N; k++){
        c[k] = b[k];
        for(int j=0; j<k; j++){
            c[k] -= L[k][j] * c[j];
        }
    }

    // Ux=cの下から順にxを求める
    for(int k=N-1; k>=0; k--){
        x[k] = c[k];
        for(int j=N-1; j>k; j--){
            x[k] -= U[k][j] * x[j];
        }
        x[k] = x[k] / U[k][k];
    }

    // show x
    printf("x\n");
    for(int i=0; i<N; i++){
        printf("%.5lf ", x[i]);
    }
    return 0;
}

MPI並列化を施したものは授業の課題そのものになってしまうため載せない。

LU分解、前進消去、後退代入とそれぞれ手計算でやる分には迷うことは何もないのであるが、繰り返し同一の処理を行うプログラムとして表現されると直感から外れるので理解に手間取った。手計算ならば3x3行列で l_{32}=\frac{a_{32}-l_{31}u_{12}}{u_{22}}と一気に要素の値を求めてしまうところ、プログラムでは l_{32}に対する -l_{31}u_{12}の処理を u_{22}に対する -l_{21}u_{12}と同一のタイミングで行っている。大きい行列の下の方になると、この減算が何回も積み重なり、最後にようやく除算(逆数を乗算)されて本当の値が求まる。

手計算では減算途中の値を書き留めるなどやっていられないので一発で要素を確定させる必要があり、減算回数が下に行くほど増えていくが、プログラムではメモリという完璧な記憶を活用して、最外ループが回るたび未確定の要素に対する段階的な減算を行っておくことができる。もちろん人間と同じやり方をしても計算の無駄は生じないのだが、PE間で行列を分散して保持している場合には u_{ij}を求めるために複数のPEにまたがって l_{ik},u_{kj}の値を送ってもらわねばならず、通信の無駄が生じる。

前進消去、後退代入においても同様に段階的な減算を行うが、行列ベクトル積の形なのでループごとの動きが容易に読めるだろう。

法医学

日本における身元不明死体の数は人口に比してかなり多い。また身元の確認ミスも起きている。顔貌による確認が主体であることに由来する。加えて高齢者の所在不明も多い。

乳歯・永久歯の萌出時期は決まっているため、生えそろい具合によって年齢を推定することができる。

個人識別の三大手段は指紋・歯科所見・DNA型であり、歯科所見は具体的に口腔内写真、レントゲン(デンタルX線)写真、デンタルチャートからなる。

CTによって口腔周辺の金属の発見ができ、インプラントや整形プレートなど身元特定の手がかりになることがある。

4歳程度までの歯は養育者のケアが必須であり、ケアがなければ齲歯(虫歯)になってしまう。これはデンタルネグレクトと呼ばれる。

ピンクの歯は自然の歯(生活歯)で、白っぽいのは根管治療を行って失活した歯である。X線撮影を行うと根管充填材は不透過なので明確に判定できる。

災害時には生前のカルテ・写真データを喪失してしまうことがありデータベース化が提言されている。

法遺伝学で行われるDNA型鑑定とはDNAの一部におけるバンドパターンなどを用いて特定に役立てるものである。Y染色体の多型(個体差)を利用して強姦事件の照合に使うこともあるが、Y染色体は親子・兄弟で共通しているため多型が稀ではなく、多くの男性で特徴が共通してしまうことがあり冤罪を生じさせうる。

科警研は以前はVNTR多型(MCT118)の鑑定であったが、現在はIdentifiler™を用いたSTR多型の鑑定に切り替わっている。同一の多型特徴を持つ二者が存在する確率は格段に下がったが、そもそも試料の採取・保存の過程におけるコンタミネーションなど取り扱いに起因する問題が生じる可能性は残っているため誤判の可能性を意識する必要がある。

現在では科捜研がDNA検査を事実上独占しており、捜査側による鑑定の公正性に懸念が生じている。

メディアプログラミング

tf-idfによる単語の重み付けを利用した特徴語抽出を行った。tf-idfは文書別に各語の出現頻度を集計し、全ての文書に広く出てくる単語はありふれたもの、少数の文書で集中的に現れる単語はそれらの文書を特徴づけるものと判断する。ただしこの手法は通常、新たに出会った文書がどの文書と類似しているかを判断することに用いられるので、出現頻度が少なすぎる語は判断に使えないとみなしてカットすることが多い。

例えばニュースサイトがジャンル分けなしに類似するニュースをリコメンドすることを考えたとき、「ネズミ」という語を特徴語として使えば、「ネズミ」という単語が含まれた新しいニュースに対しては動物や植物に関する過去のニュースをリコメンドすればよさそうだと判断することができるが、「アメリカミズハタネズミ」という特徴語は(そもそも名前の途中で分割されてしまいそうではあるが、分割されなかったとして)希少すぎるため新たに出会うニュースの中にまず出てこず利用チャンスがない。

また、たとえ頻度がある程度高くても1、2件のニュースの中でのみ何度も言及されているなら類似したニュースを見つけることには役立たないのでカットするということもありうる。

import numpy as np
from sklearn.feature_extraction.text import TfidfVectorizer
from sklearn.metrics.pairwise import cosine_similarity

corpus = np.array(wakati_news_list)  # 単語分割済みのニュース群

vectorizer = TfidfVectorizer(max_features=1000, max_df=0.5, min_df=0.05)  # 5%以上半分以下のニュースで出現する語の頻度上位1000個についてtf-idfを計算する場合
corpus_tfidf = vectorizer.fit_transform(corpus)

target_tfidf = vectorizer.transform([wakati_new_news_text])  # 先に抽出した1000個の特徴語について新しいニュース文中での重要度をベクトルで出す

similarity_matrix = cosine_similarity(target_tfidf, corpus_tfidf)[0]  # ニュース群と新しいニュースのtf-idfベクトルの各コサイン類似度が得られる

授業とは関連しないが、以前ファイル出力でf.write()やprint(file=f)を使った際に一番良いファイル出力方法は何だろうかと思った。リストとジェネレータでメモリ使用量とコストを比較するによればジェネレータは巨大なデータ群を反復的に出力するとき格段にメモリ使用量が削減できることが示されている。これは自由に要素にアクセスできないことと引き換えに全ての要素をメモリに展開せずにおくからで、Effective Pythonでもジェネレータが推奨されている。

ただし多少遅くなる。速度を求める場合はメモリに載せられる限度で長いリストをstr.joinして一回でwrite()するのが良さそうだ。write()の複数呼び出しや文字列の逐次結合は遅くなる。日常的なキロバイト、メガバイトレベルの書き込みならばwrite(str.join(list))一発でやろうと思った。

12月第2週の振り返り

12月第2週(12/9-12/15)

フランス法文献講読

préjudice(損害)とdommage(侵害された事実)は異なる概念であるとアンセル教授は述べる。日本法においては特異な相続肯定説がとられており、死亡によって生じた損害賠償請求権(逸失利益)が被害者本人から相続人に相続されるとするが、フランスを含め他国では基本的に本人は死亡しているので損害賠償請求権が発生するのではなく、扶養利益の損害賠償を各人が請求することになっている。

人的担保

保証債務の成立には主債務の成立と保証契約の締結が必要となる。保証契約は要式契約であり、書面が必要である。保証契約の当事者は債権者と保証人であり、主債務者が保証人と保証委託契約を結ぶことは必須でない。保証契約について動機の錯誤(担保があると聞いていたのになかった、そんなリスクがあるならば保証人にならなかった)による無効を主張できるのに加え、改正により主債務者が保証を依頼する際保証人に財産状況等を提供する義務に違反し、また保証人を誤認させるに至った因果関係があるとき、債権者(債権者も調査結果の説明義務を負う)が主債務者の債務や財産状況について悪意または有過失であったならば、保証契約取り消しの効果が生じるようになった。

保証債務は主債務よりも重くなることはなく、その場合は縮減される。また保証契約締結後に主債務が増えても自動的に保証債務が重くなることはない。

主債務に生じた事由は保証債務にも影響する(主債務の時効の更新・完成猶予が保証債務にも及ぶ。逆に保証人が主債務の時効の援用をすることもできる)。保証人について生じた事由は相対効であり、主債務者に影響を与えない(弁済を除く)。そのため保証人に催告・訴訟提起をしても主債務の時効には影響がない。

保証債務には補充性があり、保証人は催告・検索の抗弁を行うことができる(連帯保証では否定される)。

保証人は主債務者が利益を受けた限度において主債務者への求償権を有する。ただし委託保証人が事前・事後の通知義務を懈怠した場合は求償が制限され、それぞれ抗弁を有していた分の求償不可、債務者への一切の求償不可となり、債権者に不当利得の返還請求を行うことになる。

個人根保証は保証人の保護のため極度額を定めずに契約したものは改正後無効となった。

三者が債務を消滅させようとする場合、複数の方法がある。

(債権者と保証契約を締結し)無委託保証を行い弁済するならば、現存利益の範囲で求償することができる。

債務を引き受けるには、併存的債務引受:引受人との間に新しい債務を設定する(原債務者との間に連帯債務関係が成立する)ものと、免責的債務引受:債務者の地位が引受人に移転する(原債務者は債務を免れる)ものの2種類がある。

前者は連帯債務関係であるから(引受人の負担部分を超えた範囲で)求償権が発生し、また債務者による契約取消・解除権の行使前の債務履行を引受人は拒絶できる。また債務者-引受人間の合意により行った債務引受は、合意が強迫によるものだったなど引受契約の無効・取消事由をもって債権者に対抗できる。債権者-引受人間の契約による場合、債務者-引受人間の原因関係から生じる事由をもって債権者に対抗することはできない(契約の条件とされている原因関係は例外)。

付従性や補充性がないことの違いはあるが、債務負担の合意がなされている場合に保証との区別が困難である。そのため保証目的の引き受けであるならば保証に求められる規定の潜脱を防ぐような処理が求められる。

後者は債務者が移転し、加えて債務の元となった契約の取消・解除権も移転する。求償することはできない。

債務の更改は免責的債務引受に似るが、更改契約という1つの法律行為によって旧債務の消滅と新債務の成立が実現する。新債務は旧債務と同一ではなく、担保は当然に移転することはない(ただし更改契約に特約があれば質権・抵当権に限り認められる。人的担保は責任消滅)。

三者弁済は債権者との契約なく弁済するもので(とはいえ債務者との委任契約に基づく事務処理費用償還:650条または事務管理に基づく費用償還:702条の形で求償権は発生する)、担保不動産の第三取得者のように債務が履行されないと自分が(法律上の不利益を受けて)困るという者=正当な利益を有する第三者は無条件で認められる。そうでない場合、例えば債務者の家族を脅して弁済させることを防ぐために、債務者の意思に反して弁済することはできない。ただし債権者がそのことについて善意であれば有効である。こうした不安定さを考慮して、改正により債権者は拒絶することができるようになった。

並列プログラミング

 Ax=bとなるxを求めるには行列操作によって厳密解を求める直接解法と、近似解を反復的に計算することで収束させ求める反復解法がある。

直接解法としてGauss-Jordan法がよく知られている。係数を一つずつ消去したのち残った a^{*}_{ii}x_{i}=b^{*}_{i} a_{ii}で割って x_{i}を求めることになる。

これを多少高速化したものが手で計算する場合によく使われるGaussの消去法(掃き出し法)で、対角成分だけを残すように引き算を繰り返すのではなく、上三角行列になるようにする(これにより係数消去時の計算回数が減る)。最後の項 a^{*}_{nn}x_{n}=b^{*}_{n}から順番にxを求める。

LU分解法は行列演算として定式化したもので、A=LUに分解し、 Ax=b\\(LU)x=b\\L(Ux)=bここで Ux=cとおき Lc=bで上から順にcを求める。そして Ux=cより最下段から順にxが求まる。

異なるb'が与えられたとき、LUは既に分解されているのでLc'=b'となるc'を求め、Ux'=c'となるx'を求める。このようにLUは最初に一度分解すれば使い回すことができるので高速化が図れる。

どのようにA=LUと分解するかについては、3種類の手法が知られている。外積形式Gauss法、内積形式Gauss法、Crout法がある。外積形式Gauss法(Doolittle法)が並列化に向く。これはGaussの消去法と同じやり方である。ただしLの対角成分は1と仮定しておく。すると \begin{pmatrix}a_{11}&a_{12}&a_{13}\\a_{21} &a_{22}&a_{23}\\a_{31}&a_{32}&a_{33}\end{pmatrix} =\begin{pmatrix}1&0&0\\l_{21}&1&0\\l_{31}&l_{32}&1\end{pmatrix}\begin{pmatrix}u_{11}&u_{12}&u_{13}\\0&u_{22}&u_{23}\\0&0&u_{33}\end{pmatrix}から u_{11}=a_{11},\ \ u_{12}=a_{12},\ \ u_{13}=a_{13}、次いで a_{21}=l_{21}u_{11}より l_{21}=\frac{a_{21}}{u_{11}},\ \ l_{31}=\frac{a_{31}}{u_{11}}、今度は u_{22}=a_{22}-l_{21}u_{12},\ \ u_{23}=a_{23}-l_{21}u_{13}と交互にUとLを計算していく。

こうして得られていくLUを一つの二次元配列で以下のように記録する。 \begin{pmatrix}u_{11}&u_{12}&u_{13}\\l_{21} &u_{22}&u_{23}\\l_{31}&l_{32}&u_{33}\end{pmatrix}
Lの対角成分は1なので記録する必要はない。

法医学

異常環境による死ということで熱傷死・焼死・熱中症・凍死について。

第1度熱傷:日常的に生じうるやけど。毛細血管の拡張・充血による紅斑が生じる。

第2度熱傷:血漿が血管外に滲出し水疱が形成される。真皮深層に至ると治癒時に瘢痕を残す。

第3度熱傷:真皮を含む皮膚全層が熱によって凝固し壊死する。血管も熱凝固しているため水疱が生じない。2-3週で瘢痕を残して治癒する。

第4度熱傷:炭化であり、熱湯では生じない。

第1-2度熱傷は血流によって生じるため(死直後の心臓が動いている間はまだ生じうるが)生活反応として使うことができる。

第2度熱傷が体表の20%に及ぶと血圧が低下し熱傷性ショック状態となりうる。50%以上で死に至る。第3度では1/3以上で死亡する。致死的かどうかの判断は第3度熱傷面積パーセント+第2度熱傷面積パーセント*1/2+年齢というburn indexで計算することがある。

熱傷性ショックは循環血液量減少、熱傷組織から出た酸化脂肪酸のような熱傷毒、溶血、敗血症などの病態をとる。

面積の目安としては「9の法則」と言って頭部、各上肢、各大腿、各下腿が9%、背中前後それぞれ18%、掌で1%という概算ができる。

重度の熱傷を負うと皮膚が縮み、胸腹部であれば呼吸阻害、手腕部であれば血流減少による壊死が起こるため、皮膚を切り開いて防止する減張切開が行われる。

火事においては熱傷死だけでなく、有毒ガスの吸入や酸素欠乏による複合的な要因による焼死が生じうる。そのため前述の第1-2度熱傷気道熱傷や血中一酸化炭素ヘモグロビン(COHb)といった生活反応によって判断する必要がある。

屈筋が熱凝固により強く収縮して拳闘家肢位と呼ばれる姿勢をとる。また皮膚が裂けたり腹腔内での水蒸気発生によって腸管脱出が生じることがある。皮膚の収縮によって行き場を失った血液の圧力で静脈洞が裂け、熱凝固した硬膜外にレンガ色・赤褐色(高熱による凝固の色)の血腫として付着する(外傷性血腫は黒色であり、しばしば骨折を伴う)。これらは生活反応ではない。

熱中症は体温調節中枢が働かなくなり臓器の機能不全に至るもの。

凍傷は-2℃以下で発生し、組織が凍結→融解→炎症と壊死という過程を経る。凍瘡(しもやけ)は低温刺激による血管拡張・鬱血であり、8-10℃で生じる。凍傷も第1度の紅斑性、第2度の水疱性、第3度の壊死性に分けられる。第2度までは瘢痕を残さず治癒する。

低体温症による凍死は水中なら15℃程度でも生じる。5℃では数時間で死亡する。直腸温30℃以下で危険になる。胃粘膜の点状出血(Wischnewski斑)や鮮紅色の死斑、右心室と比べ左心室の鮮紅色血液が認められる。

感電死は電流による心室細動、呼吸筋痙攣・呼吸中枢麻痺による窒息死、熱傷の合併症が原因となる。交流、特に40-150Hzが最も危険である。所見として熱傷と電流斑(黒凹-蒼白隆起-紅斑という特異なもの)があるが、水中の感電など面積が広い場合は発現しない。

メディアプログラミング

今週はテキスト分析。形態素解析janome言語モデルをnltkで演習する。連続する名詞など、複数の単語境界が考えられる場合の分割方法はいくつか考えられてきた。分割数が最小になるようにするもの、最長一致する単語を選択するものなどがあり、Viterbiアルゴリズムと呼ばれるものでは生起コストと連接コストの和が最小となるように単語分割を選択する(≒最も頻度の高い単語の連なりを選ぼうとする)。

janomeでの形態素解析は簡単で、

t = janome.tokenizer.Tokenizer()
t.tokenize(string)

だけで終わる。

言語モデルは入力された文の生起確率を返すモデルで、素朴なものとして統計的単語n-gramがある。n=2の場合ある単語に続いて当該単語が来る確率を学習コーパスを用いてあらかじめ計算しておき、入力文の評価は分割したのちにそれぞれの単語の組み合わせが生起する確率の総乗で算出する。

 nltkを用いて学習させ、特定の単語からなる文を生成させるには

from nltk.lm import Vocabulary
from nltk.lm.models import MLE
from nltk.util import ngrams

n = 3

vocab = Vocabulary(1d_vocab_list)

text_trigrams = [ngrams(word, n) for word in words]  # wordsは分かち書きによって得た単語リスト

lm = MLE(order = n, vocabulary = vocab)
lm.fit(text_trigrams)
context = ["親", "譲り"]
while(True):
    w = lm.generate(text_seed=context)
    context.append(w)

    if '。' == w:
        print("".join(context))
        break

とすれば得られる。

12月第1週の振り返り

12月第1週(12/2-12/8)

フランス法文献講読

patrimoine: (個人の)資産・遺産、(社会的な)遺産

fixer: 約定する(・固定する)

liquidité: 流動資産

cession: 譲渡(消極財産=負債についても同じ語が用いられる)

フランス民法典(2016年改正後)では、契約の解釈について指示を与えている。例えば1188条前半では


Le contrat s'interprète d'après la commune intention des parties plutôt qu'en s'arrêtant au sens littéral de ses termes.

契約は、その文言の字義に拘泥するよりもむしろ、当事者共通の意図に従って解釈される。

と規定されている。日本法でも当事者の意思を推定することは行われているが、それが明示的に指示されているというのは一つの違いとして存在する。

担保物権

約定担保物権である質権に対して、法定担保物権としては民事・商事留置権がある。他人の物を現に占有していて、その物に関して生じた(牽連性がある)債権を有している場合に、物を留置することで弁済を促す。商事留置権では商人間の継続的取引を念頭に、牽連性を問わず債務者の所有する物を留置できる(売掛金弁済まで借地を返還せず留置など)。留置物は保存に必要な使用・債務者の承諾に基づく使用であれば可能だが、無断使用や賃貸は認められない。優先弁済効もない(ただし競売にかけて換価金返還または被担保債権との相殺ができる)。

分割債務においては債務者各人の負う債務は自己のものだけで、債権者は各々の債務の履行を当該債務者以外に求めることはできない。これを法令・特約によって連帯債務とすると、債権者は債務者の誰に対しても全部履行の請求が可能である。その債務者は全部履行を行った後、他の債務者に対して負担割合に応じた求償権を有する。

不可分債務は物理的に債務の内容が不可分である場合(自動車の共同購入)と、平等の観点(共同相続した賃借権で、賃借人としての地位は分割できないのに、分割債務を認めると各々半額しか払わなくてよくなる)から不可分とすべき場合があった。

しかし潮見によれば債権法改正後は絶対的効力事由が連帯債務と同一になった(連帯債務の絶対的効力事由が削減された―履行の請求によって生じる消滅時効の中断や履行遅滞の効果は他の債務者に及ばなくなる、債務者一人に対し債務を免除しても他の債務者に請求できる額は変わらなくなる)ため、後者の場合は単に連帯債務とすれば足りるという。

つまり従来は不可分債務と可分債務の間に連帯債務があり、この連帯債務には債権者側(免除が他の債務者にも影響)にも債務者側(あずかり知らぬ履行遅滞)にも不都合な点があったが、これらの点を解消したことで不可分債務と連帯債務とは名称の違いだけとなり、物理的に不可分なら不可分債務、そうでなければ連帯債務と呼ぶことになったと私は理解する。

また改正により、連帯債務で一部弁済を行った場合には自己負担部分を超えなくても求償可能になった。仮に100万円の連帯債務をA, Bが半分ずつ負担しているとき、Aが50万円の一部弁済を行っても、残りの50万円についてなお請求を受けうるが、改正前では求償ができるのはさらなる弁済を行ってからになる。改正後では一部弁済の段階で求償できるので、より公平であり、また履行の促進につながるとされる。

並列プログラミング

Cannonのアルゴリズムを用いて、分散して個別メモリに持っている部分的な配列を隣接するPEと送受信する。

各PEは行を分担して対角成分から計算を始める。計算が完了したら行列Cにおける行方向に移動して新たな部分の計算を行う。そのためには一つ右のPEが持っているBの列を使う必要があるため受信する。また左のPEは自分が持っているBの列を必要とするので送信する。これをPEの数ぶん繰り返す。

MPI_Recv/MPI_Sendはブロッキング処理なので、全PEにおいてMPI_SendしてからMPI_Recvするように書くとどのPEも受信待機になっておらず永久に送信が完了しない。そのため偶数PEではSend-Recv、奇数PEではRecv-Sendとする必要がある。ノンブロッキング処理であるMPI_ISendもあるが、それは後日扱われる。

法医学

入浴中の死亡原因究明によって給湯器の欠陥などが判明するように、死因究明制度は消費者安全とも関わっている。

死亡、30日以上の傷病、一酸化炭素中毒、火災は消費者事故における重大事故と位置付けられ、製造者・輸入者また行政機関の長は直ちに報告する義務を負う。

死因・身元調査法では、死因の究明によって同種の被害が起きうることが分かった場合に関係機関に通報することとなっている(不慮の外因死の中に消費者事故が含まれていることがある)。

メディアプログラミング

今週は音声信号処理ということでまず音に関する座学を行い、その後pyaudio/wave/numpy/librosaを用いて演習を行った。

音の聞こえ方について、あぶみ骨からの距離によって対応する音の周波数が変わってくるが、高音になるほど広い音の高さをわずかな距離で感じ取っているため聞き分けが難しくなる。とはいえ高周波数の音をカットするとこもった音になる。人間の発話の場合、一般に4KHz以下の音があれば内容を聞き取ることができるとされる。

周波数情報を保って収録するためには、サンプリング周波数Fは収録したい音の高さ=最大周波数 f_{max}Hzの二倍以上必要(標本化定理)である。これは周波数 fの音は周波数 F-fHzの音と区別ができない(折り返し雑音=エイリアシング)ことに由来する。収録できないというわけではないので注意。そのため f_{max}Hz以上の音を除去する(高音ノイズを入れてしまうと低音と区別ができないので)ローパスフィルタを通した音を 2f_{max}Hz以上でサンプリングし収録する。理想的なローパスフィルタを通すとナイキスト周波数以上の音は存在しないので、収録した信号を用いてその帯域制限を満たす信号=元の波形が一意に定まり復元できる。

ビット深度は音をデジタル信号として記録するにあたって振幅(音の大きさ)を離散化(量子化)するときの階調の細かさに影響する。2ビットであれば、0-1-2-3であるから基準の大きさ2から正負1段階、すなわち2階調しか表現できないことになる。このようにビット深度が小さい(すなわち表現できる最大音量と最小音量の差=ダイナミックレンジ=信号波と量子化ノイズの比が小さいことになる)と、音圧記録時の丸め誤差によって各時点で本来と異なる音圧に復元されて表現されることとなり、ノイズとして感じられるようになる。

普段目にするdBは相対的な音の強さであり、絶対的な音圧はdB SPLとして騒音計で計測される。騒音計の計測モードには複数の特性があり、A特性は人間の聴覚特性に類似するように重みづけして評価する。

人間の聴覚では位相のずれを区別できない。しかし逆フーリエ変換で周波数領域(ある時点における周波数ごとの振幅の大きさ)から時間領域(時間経過による振幅の変化)に戻す際には位相の情報が必要になる。

どの母音かは周波数スペクトルのなだらかな(大局的な)変動であるスペクトル包絡のピーク(フォルマント)位置によって区別できる。

pyaudioではファイルストリームに送るチャンクサイズを変更することで「バッファリングが間に合わない」現象を再現し、途切れ途切れに再生されることを確認した。

import pyaudio

wavfile = wave.open(filepath, 'rb')
p = pyaudio.PyAudio()
stream = p.open(format=p.get_format_from_width(wavfile.getsampwidth()),
                channels=wavfile.getnchannels(),
                rate=wavfile.getframerate(),
                output=True)

chunk_size = 16

data = wavfile.readframes(chunk_size) # chunk_sizeフレーム分取得する
while len(data) > 0:
    stream.write(data)
    data = wavfile.readframes(chunk_size) # 次のチャンクを取得
    
stream.stop_stream()
stream.close()
p.terminate()

高速フーリエ変換はnumpyで提供されている。波形を周波数成分に分解するのは以下のようになる。

wavfile = wave.open(filepath, 'rb')
x = wavfile.readframes(wavfile.getnframes())
sampling_rate = wavfile.getframerate()
sample_size = wavfile.getsampwidth()  # サンプル幅(byte)
wavfile.close()

x = np.frombuffer(x, dtype= "int16")
x = x/(2**(8 * sample_size) / 2)  # 振幅の正規化

X = np.fft.fft(x)

amplitude = 20*np.log10(np.abs(X))  # 相対音圧で算出
x_axis = np.fft.fftfreq(len(X), d=1.0/sampling_rate)  # len(X)で得られるのはビン数なので、周波数の値に変換する
ax.plot(x_axis[0:int(len(X)/2-1)], amplitude[0:int(len(X)/2)-1])  # ナイキスト周波数以上は省略したい

周波数分解は時間によって周波数成分が変化しない音の分析には適するが、高低が変化する音楽では時間によって変化する周波数成分が全て混ざって分析されてしまう。そのためある瞬間の音(1サンプル)だけで分析したいところであるが、それは不可能なのでごく短時間で区切った上で前後の波形の影響を弱める手法をとる。これを短時間フーリエ変換(STFT)と呼ぶ。matplotlibには時間経過による周波数成分の変化をグラフにするスペクトログラム描画機能がある。

wavfile = wave.open(filepath, 'rb')
x = wavfile.readframes(wavfile.getnframes())
x = np.frombuffer(x, dtype= "int16")
sampling_rate = wavfile.getframerate()
wavfile.close()

N = 512  # フレーム幅
hamming_window = np.hamming(N)

plt.specgram(x, NFFT=N, Fs=sampling_rate, noverlap=0, window=hamming_window)

パワースペクトルの大域的な動きの特徴をケプストラム特徴といい、人間の周波数感度を模したメルフィルタを通して特徴量を描画したものがメル周波数ケプストラム係数(MFCC)となる。

import librosa
import librosa.display

y, sr = librosa.load(filepath, sr=sampling_rate)
mfcc = librosa.feature.mfcc(y, sr=sr)

librosa.display.specshow(mfcc, sr=sr, x_axis='time', vmax = 100, vmin = -600)

色の分布が男性と女性、ピアノとヴァイオリンなどで異なっていることが分かった。

11月第5週の振り返り

11月第5週(11/25-12/1)

フランス法文献講読

Il arrive que: 非人称 ~ということがある(起こる)

droitが法という概念を指すのに対してloiは形のある法律を意味する。

élément d'actif: 積極財産

担保物権

ほとんどの動産には登記制度がないため、抵当権は設定できない。また質権は占有権を質権者に移転することになるため当該動産を使用できなくなってしまう。動産を譲渡担保の目的物とすれば所有権を移転する(正確には譲受人のために譲渡人が代理で占有しておく占有改定によって引き渡したこととする)ので担保権者が設定者に賃貸する形をとって使用を続けることができる(質権でも同じことをすればいいように思えるが質権の設定は要物契約であり、現実の引渡しが必要とされているため不可能)。

ただし譲渡担保では設定者の手元に動産があるため第三者の善意取得が起き得る。動産譲渡登記を行うことで対抗できる。

動産を売買しその代金債権が弁済されない場合に競売を申し立てることができる(動産売買先取特権)。ただし第三者に動産が引き渡されたときには不可能になる(買主の処分権の承認)。その代わり、物上代位をして転売代金債権を差し押さえることができる。

動産売買先取特権は法定担保権であり公示がないので、転売代金債権がさらに譲渡・通知されてしまった(譲受人が第三者に対する対抗要件を備えた)場合は譲受人が先取特権を知る術がないため保護され、差し押さえることはできなくなる。他方転売代金債権が第三者によって(抵当権などで)差し押さえられた場合は優先弁済効力を主張できる。と思いたい。もはやわからん。

所有権留保売買は弁済がなされなかったとき目的物を引き揚げ清算を行う。破産手続き上も別除権者として扱われ、清算金を管財人に支払って返還を求めることができる。

ファイナンス・リースは中途解約ができず、リース物件から得られる利益とコストのどちらも借り手のものとする。簿記の記憶が...

並列プログラミング

行列-行列積を並列化する。ナイーブにC=ABを計算すると、Aの行ベクトルとBの列ベクトルの内積を並列で計算してCの要素として格納することになる。Bに対するメモリアクセスは列方向であり性能が低下するのでBを転置しておくのが望ましい。

このナイーブな方法以外に、行列をキャッシュに格納できる大きさまで分割し通信・放送を通じて並列計算を実現するものがあり、代表的なものとしてCannonのアルゴリズムとFoxのアルゴリズムがある。それぞれ隣接するPEに通信・全PEへの放送を用いることになっており、計算機のハードウェア設計によってどちらが適しているかが異なる。京は上下左右前後の隣接PEへのネットワークで接続されているのでCannonが、Oakforest-PACSはスイッチに集約しているためFoxが適している。

法医学

頚髄が損傷すると呼吸筋が麻痺するため、創による失血よりも前に死亡することがある。

いわゆる擦過傷は表皮剥脱と呼ばれるが、タイヤの轢過など圧迫によっても生じることがある。生活反応として利用可能である。赤みを帯びたり、黄褐色(リンパ液)のかさ痂皮が認められる場合は生前に生じたものとなる。

皮下出血は外表上に変色が認められなくても生じていることがあり、背中を含めて確認することが重要となる。痣で観察できるように、最初は青紫だが黄色くなってやがて褪せる。

棒や鞭などで打撃が加えられると血管中の血液が左右に押し出されて皮下出血となる二重条痕が生じる。

挫創は皮膚と皮下組織が挫滅されてできたもので、骨が浅いところにある時によく生じる。内臓の損傷である挫傷と区別する必要がある。

交通事故では衝突・跳ね上げ・転倒の三次にわたる損傷が生じる。加えてタイヤや車底に轢過されることで前述のタイヤマークやデコルマン(decollement: 皮膚表面の引っ張りによって皮下組織が断裂する)が生じることもある。乗車人員はガラス損傷を負うことが多く、右側座席は身体の右側に生じるので運転者の特定に役立つ。またハンドルへの衝突によって肋骨骨折・大動脈破裂・心挫傷なども起きることがある。

銃創も鈍器損傷に含まれることがある。接射では燃焼ガスが皮膚を放射状に割く。近射(50cm~1m以内)では火薬粒・煤が射入口付近に貫通する。しかし肌が露出している場合ではともかく、厚い服を着ていた場合には近射であっても火薬粒が服に防がれることがある。

特に骨を貫通した場合、斜めに射入した場合には射入口にも骨の粉砕が生じうるが、そうでない場合射入口は綺麗な穴となる。

散弾の場合は銃口から出て数十センチでシェルに詰められたものが散らばるため、接射では射入口が一つになることがある。

メディアプログラミング

今回は時系列データ解析ということで、Jupyter Notebook上でpandas/matplotlib/mpl_financeを用いてcsvからローソク足移動平均2種類を重ねた上で軸表示をカスタムして表示させることを行った。以下のコードはデータの読み込みやplt.figure()の準備などお決まりの部分は省いてある。

import pandas as pd
import matplotlib.pyplot as plt
import matplotlib.dates as mdt
import mpl_finance
from datetime import datetime
from matplotlib.dates import MO

pd.plotting.register_matplotlib_converters()  # Pandasのdatetime形式をmatplotlibの単位リストに登録する(警告が出なくなる)

start = datetime(2019, 11, 1)
end = datetime(2019, 11, 30)
df["date"] = pd.to_datetime(df["date"])  # datetime64へ変換
df.set_index('date', inplace=True)  # 時系列データを扱っているので日付はインデックスとしてデータとは別の扱いにしたいし、時系列での移動平均の計算には明示的にインデックスの設定が必要
# cf. https://pandas.pydata.org/pandas-docs/stable/reference/api/pandas.DataFrame.rolling.html
# 移動平均
df["mean_5d"] = df.loc[:, "close"].rolling(5).mean()
ax.plot(df[start:end].index, df.loc[start:end, "mean_5d"]) 
# ローソク足
ohlc = df.loc[start:end, ["open", "high", "low", "close"]]
ohlc.index = mdt.date2num(ohlc.index.to_pydatetime())  # 紀元からの経過秒数(candlestick_ohlcはfloat形式のtimeが必要)
mpl_finance.candlestick_ohlc(ax, ohlc.reset_index().values)  # DataFrameではなく二次元配列に。引数はaxisのあとtime, open, high, low, closeの順で並ぶ必要がある。reset_indexはindexを解除して既存データの先頭に組み入れる
# 表示スタイル
# 主軸を月曜の日に置く
locator = mdt.WeekdayLocator(byweekday=(MO))
ax.xaxis.set_major_locator(locator)

ax.xaxis.set_major_formatter(mdt.AutoDateFormatter(locator))  # 表示ロケール・サイズは自動

ax.xaxis.set_minor_locator(mdt.DayLocator())  # 補助軸は日ごとに置く

fig.autofmt_xdate()  # 目盛り間隔に応じてx軸の値表示を調整

今回は移動平均ローソク足を同時に処理したかったためindexを設定してから解除したが、ローソク足だけであれば直接dateをfloatに変換してvalues()で渡せばよい。

11月第4週の振り返り

11月第4週(11/18-11/24)

フランス法文献講読

契約の自由は絶対的(absolu)なものではなく、締結を強制される契約がある(保険など)が、契約としての性質を妨げられるわけではない。とはいえ契約の相手方も、締結することも定められている(=意思が存在しない)契約は自由が見当たらず、ほぼ契約とは呼べないのではないのではないか、とはパスカル・アンセル教授談。

担保物権

抵当権が実行されると競売にかけられるが、時間がかかりまた落札額が評価額を下回ることがあるため、代わりに抵当直流れの特約といって所有権を直接移転することができる。

不動産譲渡担保は設定時点で所有権が移転するのでこれとは異なる。しかし不動産譲渡担保も弁済期到来までは実質的に設定者が所有者としての権限を保持する(登記上は移転)。弁済を行うと目的物の権利を取り戻すことができ、これを受戻しと呼ぶ。しかし、弁済期到来後に担保権者(債権者)が不動産を処分した場合は当然受戻すことができない(なにしろ期日までに弁済していないので)だけでなく、弁済後の譲渡であっても登記を戻さなければ第三者に対抗できない。

並列プログラミング・法医学

残念ながら休講であった。

セキュアプログラミング

扱われていた多くの事柄は現代的なフレームワークでは対策が組み込まれており、開発者が作成する部分に起因する欠陥といえばセッション固定攻撃、クリックジャッキングあたりであろうか。自らのサイトが直接攻撃にさらされるだけでなく、正常な遷移と誤認させるために利用されうることも意識する必要がある。

11月第3週の振り返り

11月第3週(11/11-11/17)

フランス法文献講読

フランス語の括弧にあたるguillemet «および»が日本語版Wordでは置換時に限り自動的にdouble quote"に変わってしまい、OCRで得られた一貫性のない括弧―≪(不等号much-less-than)と«(guillemet)―のスタイルを揃えるのにわざわざVSCodeに移して置換することになった。望んで置換しているのだから文字を勝手に変えるのはやめてほしいものだ。使用者のロケールに合わせて一貫性を持たせようとしているのかもしれないが、それならせめて入力されるすべてのguillemetを初めからdouble quoteに自動変換してほしい。

WordのCtrl+(Shift)+記号キー→アルファベットでアクサン・セディーユが入力できるのは大変便利なのでVSCodeに全面的に移行するわけにもいかず、置換の時だけ力を借りることになりそうだ。

sans l'avoir voulu: 望んでいなくても

mal informer: 不十分な情報提供を行う

le plus souvent: たいてい

fait personnel/d'autrui/de chose: 個人的所為=行為/他人の所為/物の所為=作用(製造物責任fait du produit défectueuxなど) ※これら3つを総称してfaits générateurs de responsabilitéという。物の責任を人に帰着させずにそのままでとらえるとのこと。

réparation(賠償)にはdommages-intérêts(損害賠償=金銭賠償)とréparation en nature(現実賠償=原状回復)が含まれる。

フランスでは行為責任はなく、あくまでfaitであるが、responsabilité délictuelleは適切な訳がないので不法行為責任と訳される。

toujour: 相変わらず(・いつも)

担保物権

借地上の建物に設定された抵当権は、従たる権利である建物の借地権に及ぶ。それに対し自己所有の土地に建てた建物には借地権が付随しないため、差し押さえによって建物の所有者が移転するとそのままでは土地占有権原がなく不法占有状態となってしまう。そのため建物の保護を目的として法定地上権という制度があり、土地建物が同一所有者に帰属し、抵当権設定時に既に建物が存在し、かつ実行時にも存在している上で、法定地上権の成立によって利益を害される第三者(土地が共有持分であるなど)がいないときに成立する。

抵当権設定後の賃貸借は抵当権に劣後する。そのため競落後明け渡さなければならないが、建物明渡猶予制度により6か月間に限り買受人に賃料相当額を支払って明け渡しを拒むことができる。

並列プログラミング

固有値問題の数値解法である冪乗法を扱った。

 Ax=\lambda xとなるλ, xを求めたい。n×nの行列Aに対して固有ベクトルはn本あり、それぞれ直交である。そのため任意のベクトルuは u=c_{1}x_{1}+...+c_{n}x_{n}で表すことができる(cは係数)。

 Au=A(c_{1}x_{1}+...+c_{n}x_{n})であり、 Ax_{i}=\lambda x_{i}であるから、 Au=c_{1}\lambda_{1} x_{1}+...+c_{n}\lambda_{n} x_{n}が成り立ち、これをλ1でくくると Au = \lambda_{1}(c_{1}x_{1}+c_{2}\frac{\lambda_{2}}{\lambda_{1}}x_{2}+...+c_{n}\frac{\lambda_{n}}{\lambda_{1}}x_{n})となる。

ここでAuをk乗すると (Au)^{k} = A^{k}u = \lambda_{1}^{k}(c_{1}x_{1}+c_{2}(\frac{\lambda_{2}}{\lambda_{1}})^{k}x_{2}+...+c_{n}(\frac{\lambda_{n}}{\lambda_{1}})^{k}x_{n})となり、λが大きいほうから並んでいるとすれば、x1以外のベクトルが小さくなっていく。すなわち最大の固有値固有ベクトルに収束する。

法医学

縊死には定型的縊死と非定型的縊死があり、空中に完全に懸垂され、結節がある場合は頸部正中線上にあるものが定型的。地面に足がついている場合は非定型となる。頸動脈(5kg)・椎骨動脈(16kg程度)の閉塞によって意識が即座に消失する。

定型的縊死では全体重が頸部に集中して動脈が閉鎖するため、顔面は蒼白となる。非定型的縊死では不完全な閉鎖が生じることがあり、その場合は頭部に鬱血する。

溺死に関連して、淡水は溶結を引き起こすため細胞障害が重篤になる。これは花粉症の鼻洗浄にも言えることで、生理食塩水が用いられることで細胞障害を防止している。淡水で行ってはならない。

溺死は長時間持続する所見がなく当初微細泡沫塊・血中塩素イオン濃度、次いで溺死肺・胸腔内血性液・血液比重、最終的に諸臓器からのプランクトン検出に頼らざるを得なくなる。しかし風呂水では検出できない。

創=開放性損傷(外部から観察可能)、傷=非開放性損傷。

創は密着させないと所見として意味をなさない(創を生じさせた成傷器の幅や、創の順番など)。

鋭器損傷には切創(incised wound:皮膚面に平行に切断する、創口の長さが深さより長い、成傷器の推定が難しい)・割創(刃物を打ち付ける)・刺創(puncture wound:尖端を有するもので垂直に刺す、創洞の深さが組織の弾力性により変動するため解剖時と異なる場合がある)

今週はまだ新しい授業が始まっていないのでこれでおしまい。