do-release-upgradeによるUbuntuアップグレードで「修復不可能な問題」と表示された時の対応

f:id:swytel:20180507150208p:plainUbuntu 14.04LTSから16.04LTSにアップグレードすべく、次のサイト等を参考にdo-release-upgradeで実施したところ、Ubuntu非公式レポジトリを有効にしていたために、ハマったのでメモ.

まずは、上記ブログにもあるように、バージョン確認をしてから、現行システムの更新を行い,マシンを再起動しました.

$ lsb_release -d
Description:    Ubuntu 14.04.5 LTS
$ sudo apt-get update
$ sudo apt-get upgrade
$ sudo apt-get dist-upgrade

さらに、下記の方法で、リリースチャネルの確認と設定をします.

$ cat /etc/update-manager/release-upgrades

自分は、最下行が"Prompt=never"になっていたので、viで上記ファイルを開き、"

Prompt=lts

に変更しました。

しかしその後

$ sudo do-release-upgrade

としたところ、次のエラーが表示されてしまいました。

f:id:swytel:20180507150208p:plain

自分が実行しているのは14.04LTSで、リリース前のUbuntuを実行しているわけはありませんが 3番目の

* Ubuntu以外から提供されている非公式パッケージ

には、心当たりがあります。しかし、どの非公式パッケージを入れたか、またどうやって削除するかが分からない.

結論から言うと,Canonicalパッケージやextrasが悪さをしているようでした. 自分は,これらのレポジトリに関する記述をコメントアウトすることで,先に進むようになりました.

$ sudo vi /etc/apt/sources.list
(次の行をすべてコメントアウト)
# deb http://archive.canonical.com/ubuntu trusty partner
# deb-src http://archive.canonical.com/ubuntu trusty partner
# deb http://extras.ubuntu.com/ubuntu trusty main
# deb-src http://extras.ubunut.com/ubuntu trusty main

以上が終わった後,もう一度

$ sudo apt-get update
$ sudo do-release-upgrade

を実行します.

これでもエラーが出る場合は,非公式パッケージ(ppa)が原因かもしれません. 私は、元々ppaが原因だと思っていたので、下記も実行しました.

askubuntu.com

によれば、コマンドラインで下記を実行することで、自分がインストールした非公式パッケージの一覧を表示させることができます.

$ grep -RoPish '(?<=ppa.launchpad.net/)[^/]+/[^/ ]+' /etc/apt | sort -u | sed 's/^/ppa:/'

自分は、これを実行したところ

ppa:jtaylor/ipython
ppa:mc3man/trusty-media
ppa:thefanclub/grive-tools
ppa:webupd8team/java

などと出てきました.

今度はこれを消去します.これには、ppa-purgeというツールを導入しておきます. PPA の追加 / 削除 - 哲朗web

$ sudo apt-get install ppa-purge

使い方としては、例えば

$ sudo ppa-purge ppa:jtaylor/ipython

などとなります。この調子で、他の非公式パッケージも削除していきます。ちなみに上記がうまくいかない場合は,次のような方法もあるみたいです. 追加した ppa のリポジトリをリストから削除する方法

sudo add-apt-repository --remove ppa:jtaylor/ipython

これでもうまくいかない方は,launchpadのppa以外に,google chromedropbox等をaptで入れたことが原因かもしれません. これらのパッケージを消すには,まずdpkgで消す,次にsources.list.d/のリストから,debで始まるレポジトリの一行をコメントアウトする,という手順を取ります.

$ sudo dpkg -r google-chrome-stable
$ sudo dpkg -r dropbox
$ cd /etc/apt/sources.list.d/
$ sudo vi dropbox.list
$ sudo vi google-chrome.list

以上を実行した上で

$ sudo apt-get update
$ sudo do-release-upgrade

で,アップグレードできるかどうか,試してみてください.

さて、私の場合、上記でアップグレードが進んだのですが、完了一歩手前というところで 「処理中にエラーが発生しました」とコンソールに表示され、次々とエラーダイアログのGUIがポップアップする事態になりました。 再起動してくださいといったダイアログもあったため、その通りにしたら まったく起動しない最悪のケースに...

もしかしたら、リブート前に、次のように対応したら良かったのかもしれませんが...後の祭り. http://tech.uribou.tokyo/ubuntu_upgrade_to_16/

というわけで、私はあまり、do-release-upgrade をお勧めしたくなくなってきました. 無事、Live USBから復活できたら、次回その方法について記載しようと思います。

ソフトバンクのキャリアメールでもBccでメール送信する方法

私はスマホiPhone)ユーザーですが、キャリアの月額料金が高く、いよいよ、MNPソフトバンクから格安SIMに乗り換えることにしました。


このとき悩んだのが、電話帳に入っている知り合いへのアドレス変更の連絡方法。私が知り合いに伝えていたアドレスは、いわゆるキャリアメール、「*@softbank.ne.jp」でした。
一方、電話帳の知り合いの連絡先も、ドコモやauソフトバンクといったキャリアメールがほとんど。私はGmailYahoo!OutlookなどのWebメールアドレスは、一通り持っているのですが、キャリアメールがこうしたWebメールアドレスを一括で迷惑メールと認識する設定になっていると聞いたことがありました。Webメールからアドレス変更通知を送信しても、受信拒否されるおそれがあります。

 

せっかく連絡するからには、メールを受け取ってほしい。そこで、キャリアメールからアドレス変更通知を出すことにしました。ここで、課題になったのが

 

MMS画面から宛先をBccにできない

 

でした。

この時代、一括送信メールの宛先をBccにするのは、マナーになりつつあります。一方キャリアメールは、一見普通のアドレスの形をしていますが、いわゆる普通のメールとは仕様が異なり、メーラー(例:iPhoneの「メール」)からBcc設定ができません。 

 

キャリアメールだけど、Bccは設定したい!これを実現させてくれたのが、ソフトバンクS!メールどこでもアクセスでした。これは、パソコンのウェブブラウザで、S!メール(*@softbank.ne.jp, *@vodafone.ne.jp)が送受信できるようになる、というものです。こんなサービスがあったんですねぇ。#これから解約ですが...(^-^;)

まず、上のサイトの「申し込み」から、利用申請しました。利用料は月額300円とありますが、よく読むと、基本パックに入っているユーザは無料とあります。自分は基本パックに入っていたので、無料で利用でき、申請してすぐ使えるようになりました。ブラウザでアクセスすると、いわゆるWebメールのような見た目。Gmailなどと比べると機能は(だいぶ)劣りますが、使えそうです。

 

次に、スマホから「S!メールどこでもアクセス」に、アドレス帳のデータを転送します。iPhoneAndroidの人なら、アドレス帳の転送用アプリがダウンロードできます。

これで、準備が整いました。あとは、Bcc欄に次々とアドレスを入力して、粛々と送信するだけです。無事、目的は果たせました。

 

利用してみて感じた、S!メールどこでもアクセスの課題(難点)を、3つ述べておきます。

1. ソフトバンク系キャリアメールアドレス(@softbank.ne.jp, @vodafone.ne.jp)の宛先が不明な時は、エラーが表示されてそもそも送信できない

宛先に複数のソフトバンク系アドレスが含まれているとき、どの宛先が犯人(笑)かを、しらみつぶしに調べる必要がありました。まずは一旦送信、不明の宛先のMAILER-DAEMONを返すという仕様にしてほしかったですネ...

2. メール作成表示欄からは、300件分のアドレスしか表示されない

私の電話帳には、400件あまりのアドレスがありました。メール作成画面の「Bcc+」をクリックして直接入力できるのは、最初の300件で、最後の100件程度はアドレス帳画面にアクセスしてからメール作成する、というステップを踏む必要がありました。(画面キャプチャがないと、伝わりにくいですね...)

これは謎の制約事項でした。どうしてこんな設計になったのか...。

 

3. アドレス入力欄は、コピペやドラッグ&ドロップができない

これも惜しい点でした。うっかり宛先欄に入力したアドレスをBcc欄に移すとき、コピペができず、打ち直しになりました。

 

...といった制約があり、400件あまりの宛先にまとめて送信!というのは叶わず、ちまちまと、宛先を10件ずつくらいに分けて確認しながら通知メールを送信していきました。

 

ここまで書いておいて、いっそmailコマンドでfromにキャリアメールを指定すれば良かったかも、という事に気づきました。Linux等に明るく、手段を持っている人は、そうすれば良いですね。

 

 

以下は余談。

 

宛先不明によるMAILER-DAEMONも沢山返ってきて、人望ないなー私、と、一瞬寂しい気持ちにもなりましたが、中には、10年ぶりに連絡が取れた人もいたりしました。最初は億劫でしたが、何かと、アドレス変更を通知して良かったと思いました。

 

しかし最近、MNP格安SIMの流行で、アドレスが変わる人が増えています。このMAILER-DAEMONの数を見て「LINEやFacebookでも連絡取れるし、別に変更通知はしなくていいや」と思っている人が多いのだろう、と感じました。おそらく、そんな状況に甘んじて、キャリア側も、もうキャリアメールの利便性向上には、あまり力を入れていないのかもしれません。むしろ、「アドレス変更通知が面倒だし、しばらくキャリアのままでいいかな...」という人もいるでしょう。キャリアメールの不便さは、格安SIM移行に対する歯止め効果も大いにある気がします。とはいえ...この効果に期待するのは、なんとも消極的、というか、後向きな姿勢のように思えます。

 

日本ガラパゴス仕様のキャリアメール。まだまだ利用者の多い、されど流出が進みつつあるキャリアメール。日本の3大キャリアは、人々が徐々に海外のWebメールサービスに移っていくのを、この先もただ黙って見ているのでしょうか。かく言う自分も、今日で10年間お世話になったキャリアとお別れですが...

 

まずは、とにかく、Bccの手段を用意してくれたソフトバンクに最後の感謝の気持ちを表し(笑)今夜は眠りにつきたいと思います。

pythonの多重リストから最頻出ラベルを取り出す


例えば以下のような多重リストがあったとする

top_list = [[0.9951, 2],[0.8845, 3],[0.8745, 1],...]

top_list内の各要素は、第1要素が精度で第2要素がラベルの組のリスト、のようなイメージ.

ここで、top_list内の最頻出ラベルを取り出したい.こんな時、pandasのSeriesを使うとこのように書ける.

from pandas import Series
Series(map(lambda x: x[1], top_list)).value_counts().index[0]

まず内側のmap(lambda x: x[1], top_list)で、内側のリストの第2要素のみ取り出したリストを生成する. 上で言う```[2, 3, 1, ...] に相当する.仮にこれをtmp_listとする.

Series(tmp_list).value_counts()で、tmp_listの統計を取ってくれる.すなわち

  4    54
  2    34
  1    27
  3    21
  ...

のようになる.index[0]で最頻出のラベル(上で言う"4")が取り出せる.

python(numpy)でL2ノルムが1になるようにする

コサイン類似度は以下で求まる.

\( cos(\vec{a}, \vec{b}) = \frac{\vec{a} \cdot \vec{b}}{ \sqrt{\sum^{n}a_i} \sqrt{\sum^{n}b_i}} \)

ここでコサイン類似度を求めるのに、毎度ベクトルのノルム(\( \sqrt{\sum^{n}a_i} \sqrt{\sum^{n}b_i}\) )を求めるのは効率が悪い. そこで予めこれが1になるようにする(→内積=コサイン類似度になる)

ベクトルのリスト \( X = (\vec{x_1}, \vec{x_2}, ..., \vec{x_n}) \) について,各々のベクトルを正規化する.numpyのlinalg.normを利用するとベクトルの長さ(ノルム)を求めることができるので、それを利用する.

import numpy as np

norm = np.linalg.norm(X, ord=2, axis=1)
X = X / norm[:np.newaxis]

np.linalg.normについて、キーワード引数ordでノルムの次元数を指定、axisでどの次元方向に和を取るかを指定できる.

  • axis=0とすれば,各列の二乗和の平方根をとった(行)ベクトルが出力される.
  • axis=1とすれば,各行の二乗和の平方根をとった(列)ベクトルが出力される.

Xをnorm[:np.newaxis]で割って終了.

なおここでnorm(横ベクトル)を縦ベクトルに転置している. 元の配列の大きさを維持する次元には":"を指定し,新たに大きさが 1 の次元を追加するところには np.newaxis を指定している.