中野智文のブログ

データ・マエショリストのメモ

BigQueryで、1000円分の切手問題を解く

背景

igcn.hateblo.jp

方法

実行は慎むこと。データ参照は0バイトだが、7000秒たっても(現時点)結果は出ない。こんなおバカなクエリをBQ様に投げて心が痛い。

WITH
  num_list AS (
  SELECT
    n
  FROM (
    SELECT
      GENERATE_ARRAY(1,1000) a )
  CROSS JOIN
    UNNEST(a) AS n),
n1 as (select n from num_list where n * 1 <= 1000),
n2 as (select n from num_list where n * 2 <= 1000),
n3 as (select n from num_list where n * 3 <= 1000),
n5 as (select n from num_list where n * 5 <= 1000),
n10 as (select n from num_list where n * 10 <= 1000),
n20 as (select n from num_list where n * 20 <= 1000),
n30 as (select n from num_list where n * 30 <= 1000),
n50 as (select n from num_list where n * 50 <= 1000),
n62 as (select n from num_list where n * 62 <= 1000),
n82 as (select n from num_list where n * 82 <= 1000),
n92 as (select n from num_list where n * 92 <= 1000),
n100 as (select n from num_list where n * 100 <= 1000),
n120 as (select n from num_list where n * 120 <= 1000),
n140 as (select n from num_list where n * 140 <= 1000),
n205 as (select n from num_list where n * 205 <= 1000),
n280 as (select n from num_list where n * 280 <= 1000),
n310 as (select n from num_list where n * 310 <= 1000),
n500 as (select n from num_list where n * 500 <= 1000),
n1000 as (select n from num_list where n * 1000 <= 1000)

select 
n1.n as nn1,
n2.n as nn2,
n3.n as nn3,
n5.n as nn5,
n10.n as nn10,
n20.n as nn20,
n30.n as nn30,
n50.n as nn50,
n62.n as nn62,
n82.n as nn82,
n92.n as nn92,
n100.n as nn100,
n120.n as nn120,
n140.n as nn140,
n205.n as nn205,
n280.n as nn280,
n310.n as nn310,
n500.n as nn500,
n1000.n as nn1000
from n1
cross join n2
cross join n3
cross join n5
cross join n10
cross join n20
cross join n30
cross join n50
cross join n62
cross join n82
cross join n92
cross join n100
cross join n120
cross join n140
cross join n205
cross join n280
cross join n310
cross join n500
cross join n1000
where 
n1.n * 1 +
n2.n * 2 +
n3.n * 3 +
n5.n * 5 +
n10.n * 10 +
n20.n * 20 +
n30.n * 30 +
n50.n * 50 +
n62.n * 62 +
n82.n * 82 +
n92.n * 92 +
n100.n * 100 +
n120.n * 120 +
n140.n * 140 +
n205.n * 205 +
n280.n * 280 +
n310.n * 310 +
n500.n * 500 +
n1000.n * 1000  = 1000

結論

バカは俺一人で十分

Mozc の日本語入力モードへの切り替えが ctrl space だと、 emacs で困ってしまう人の設定

背景

Mozc の日本語入力モードの切り替えが ctrl space だと、emacs (terminal)で使うときに mark set したいときに、 デフォルトのキーバインドとかぶって困ってしまう。

対策

Mozc の日本語入力モードへの切り替えのキーを ctrl \ にする。

bigquery で日本語の曜日のJOIN用テーブルを作成する

背景

毎度日本語で曜日を表示するためのJOIN用テーブルを作成に時間がかかるので、 コピペ用のコードが欲しい。 (JOIN用テーブルでなくifで作ったほうががテンプレートしては使いやすいかも。)

そのクエリ

#standardSQL

WITH
  _weekday_list AS (
  SELECT
    SPLIT('日,月,火,水,木,金,土', ',') AS a),
  weekday_list AS (
  SELECT
    w,
    ja
  FROM
    _weekday_list,
    UNNEST(a) AS ja
  WITH
  OFFSET
    AS w )

'2019-01-01' は何曜日か?

#standardSQL

WITH
  _weekday_list AS (
  SELECT
    SPLIT('日,月,火,水,木,金,土', ',') AS a),
  weekday_list AS (
  SELECT
    w,
    ja
  FROM
    _weekday_list,
    UNNEST(a) AS ja
  WITH
  OFFSET
    AS w )

SELECT
   ja
FROM
  (SELECT
    cast(format_date('%w', '2019-01-01') as int64) w
  ) data
JOIN
  weekday_list using(w)

参考

sucrose.hatenablog.com

colaboratory で、pycodestyle を使う

次のように、colaboratory 上に書いて実行(python3.6で確認)

!pip install flake8 pycodestyle pycodestyle_magic
%load_ext pycodestyle_magic

あとは、

%%pycodestyle

# ... ここにコード

と書いて実行。チェックの必要がなくなれば、コメントにしてしまう。

#%%pycodestyle

# ... ここにコード

PACモデルで十分な事例数とその使い方

PACモデルで十分な事例数

 \displaystyle{ m \leq \frac{\ln(1/\delta)+\ln|H|}{\epsilon} }

ここで、 mは学習事例数、 H は仮説空間、エラー率 \epsilon以内の概念モデル C \in H 1-\delta の確率で学習すること(Tom Mitchell 著 Machine Learning 7章より)。

使い方

次の様な質問に即答できる。

  • データが倍になったら何がうれしいか?
    • エラー率が半分になる
    • あるいはエラー率が目標に未達の場合、その目標の達成確率がかなり上がる。

参考

BigQuery で、ある特定の期間の日を全て列挙する

背景

BigQuery で、ある特定の期間の日を全て列挙したくなった。

方法

generate_date_array を使う。

https://cloud.google.com/bigquery/docs/reference/standard-sql/functions-and-operators#generate_date_array

例:'2018-01-01' から '2018-12-31' までの期間を array に。

SELECT
  GENERATE_DATE_ARRAY('2018-01-01', '2018-12-31') dt_list

例:'2018-01-01' から '2018-01-31' と '2018-06-01'から'2018-06-30' までの期間を array に。

WITH
  date_range AS (
  SELECT
    DATE '2018-01-01' AS start_date,
    DATE '2018-01-31' AS end_date
  UNION ALL
  SELECT
    DATE '2018-06-01' AS start_date,
    DATE '2018-06-30' AS end_date )
SELECT
  ARRAY_CONCAT_AGG(GENERATE_DATE_ARRAY(start_date, end_date)) dt_list
FROM
  date_range

例:'2018-01-01' から '2018-01-31' と '2018-01-15'から'2018-02-15' までの期間をかぶりを考慮しつつ 展開

WITH
  date_range AS (
  SELECT
    DATE '2018-01-01' AS start_date,
    DATE '2018-01-31' AS end_date
  UNION ALL
  SELECT
    DATE '2018-01-15' AS start_date,
    DATE '2018-02-15' AS end_date ),
  date_list AS (
  SELECT
    ARRAY_CONCAT_AGG(GENERATE_DATE_ARRAY(start_date, end_date)) dt_list
  FROM
    date_range )
SELECT
  DISTINCT dt
FROM
  date_list
JOIN
  UNNEST(dt_list) AS dt

例:'2018-01-01' から '2018-01-31' と '2018-01-15'から'2018-02-15' までの期間をかぶりを考慮しつつ またarrayに

WITH
  date_range AS (
  SELECT
    DATE '2018-01-01' AS start_date,
    DATE '2018-01-31' AS end_date
  UNION ALL
  SELECT
    DATE '2018-01-15' AS start_date,
    DATE '2018-02-15' AS end_date ),
  date_list AS (
  SELECT
    ARRAY_CONCAT_AGG(GENERATE_DATE_ARRAY(start_date, end_date)) dt_list
  FROM
    date_range )
SELECT
  ARRAY(
  SELECT
    DISTINCT dt
  FROM
    UNNEST(dt_list) dt) AS dt_list
FROM
  date_list