日頃の行い

個人的な日頃の行いをつらつら書いてます\\\\ ٩( 'ω' )و ////

SwiftでJSON文字列をStructのEnumやDate型にbindする

こんにちは、最近Swiftをやっていて、Scalaのコレクション操作が欲しくなってよくないなってなっています。
API等でJSON文字列を受け取って特定のオブジェクトなどにデータを入れたいみたいなのはよくあることだと思うのですが、
Swiftでやったのは初だったのでそのあたりのメモがてらの備忘録です。

SwiftのVersion

$swift --version
Apple Swift version 5.2.4 (swiftlang-1103.0.32.9 clang-1103.0.32.53)
Target: x86_64-apple-darwin19.5.0

StringやInt、Arrayのbind

文字列、数字や配列など、jsonにもある型は特段なにもしなくてもbindしてくれますね。
JSONDecoderになにも設定せずDecodableを実装したstructの変数名とkey名を合わせると勝手にbindしてくれました。

import Foundation

let data = """
{
    "a": {
        "b": "xxx",
        "b2": ["xxx", "yyy"]
    }
}
""".data(using: .utf8)!

struct A: Decodable { 
    let a: B
}

struct B: Decodable {
    let b: String
    let b2: [String]
}

let decoder = JSONDecoder()
let t1  = try decoder.decode(A.self, from: data)
print(t1)

実行

$swift main1.swift
A(a: main1.B(b: "xxx", b2: ["xxx", "yyy"]))

Date型のbind

やはりあるあるなのか、JSONDecoderにdateDecodingStrategyというものが用意されていました。
.iso8601フォーマットは既に用意されていて、そのフォーマットならそれを設定しておけば使えるみたいですね。
独自フォーマットにする場合はformattedメソッドにDateFormatterを渡してあげると良いみたいでした。

import Foundation

let data = """
{
    "a": {
        "b": "xxx",
        "c": "2020-07-08T15:00:00+09:00",
    }
}
""".data(using: .utf8)!

struct A: Decodable { 
    let a: B
}

struct B: Decodable {
    let b: String
    let c: Date
}

let decoder = JSONDecoder()
decoder.dateDecodingStrategy = .iso8601
let t1  = try decoder.decode(A.self, from: data)
print(t1)

decoder.dateDecodingStrategy = .formatted({
        let f = DateFormatter()
        f.dateFormat = "yyyy-MM-dd'T'HH:mm:ssZ"
        return f
        }())
let t2  = try decoder.decode(A.self, from: data)
print(t2)

実行

$swift main2.swift
A(a: main2.B(b: "xxx", c: 2020-07-08 06:00:00 +0000))
A(a: main2.B(b: "xxx", c: 2020-07-08 06:00:00 +0000))

Enum型のbind

Enum型はEnum型にDecodableを実装して、文字列を元にしたいのであればStringを継承しておけば良い感じでした。

import Foundation

let data = """
{
    "a": {
        "d": [
            "hoge",
            "fuga",
            "piyo"
        ]
    }
}
""".data(using: .utf8)!

struct A: Decodable { 
    let a: B
}

struct B: Decodable {
    let d: Array<D>

    enum D: String, Decodable {
        case HOGE = "hoge"
        case FUGA = "fuga"
        case PIYO = "piyo"
    }
}

let decoder = JSONDecoder()
let t1  = try decoder.decode(A.self, from: data)
print(t1)

実行

$swift main3.swift
A(a: main3.B(d: [main3.B.D.HOGE, main3.B.D.FUGA, main3.B.D.PIYO]))

かなり簡単でしたね。
これで大体のものはAPIから内部のデータに変換できそうです。
めでたしめでたし。

AstroゲーミングヘッドセットA50の電源がつかなくて困った話

無線のゲーミングヘッドセットのAstro A50を買って使っているんですが、それが電源がつかなくなり困りました。
ぐぐったら初期化っぽい方法を書いてくれている人がいて、すごく助かったのでそのメモです。

Astro A50はこれ

助かった記事がこちら

http://nepr.info/astro-gaming-astro-astro-sans-fil-a50-gen-3-ps4-pc-%E3%83%8F%E3%82%BA%E3%83%AC%E5%BC%95%E3%81%84%E3%81%9F%E3%80%82/

引用すると、

ネットで検索すると結構海外の方で同じ症状に陥っていたが復旧出来たという書き込みがあり自分も実践してみると何事もなく復旧出来てしまったのでその方法を紹介します。
①電源スイッチをon位置にする(ledランプが点灯しなくてもok)
②ヘッドセッド右側にあるgameボタンとdolbyボタンを同時押しで30秒間押したままにする
この方法(リセット?)で復旧することが出来ました

ゲームボタンがここで

f:id:arata3da4:20200426175133p:plain
Gameボタン

Dolbyボタンがここですね

f:id:arata3da4:20200426175216p:plain
Dolbyボタン

自分のヘッドホンは電源のLEDが一切つかなかったんですが、ここを30秒押したらつくようになりました。
その他なんか充電しても充電が出来ないとかそういうときにここのリセットすると直ったりしたのでよかったです。

JupyterLab上でjupyter-lspを使って補完してもらう

jupyter全然触ってなかったらjupyter labってのが出ててへーってなったりしてました。
Tabとか押したら補完してくれるんですが、もっとリッチにできないかなーと思ってらLanguageServerのextensionがあったので、今回はそれを試してみました。

動いたレポジトリはここ

GitHub - ara-ta3/jupyterlab-getting-started

$make install install/extension run

# pythonのパスがpython3じゃない場合は
$make install install/extension run PYTHON=python

で動くはずです

インストール

Installは本家を参考にやりました。
唯一困ったのは、そのままやってもpython用のLanguageServerが起動しなくて jupyter_notebook_config.json に追加したところでした。

https://github.com/krassowski/jupyterlab-lsp#installation

0. venvの設定とnode.jsの追加

デフォで入ってたpython3とnodebrewで入れたnodeを使いました。
nodeはjupyter-lspで使うらしいです。

$python3 -V
Python 3.7.6

$python3 -m venv venv

$source venv/bin/activate

$node -v
v12.15.0

1. pipでjupyterやらlspやらをインストール

$cat requirements.txt
jupyterlab
jupyter-lsp
python-language-server[all]

$ pip install -r requirements.txt
# ... 

2. jupyter extensionをインストール

$jupyter labextension install @krassowski/jupyterlab-lsp
# ...

# installされたversion
$jupyter --version
jupyter core     : 4.6.3
jupyter-notebook : 6.0.3
qtconsole        : not installed
ipython          : 7.12.0
ipykernel        : 5.1.4
jupyter client   : 5.3.4
jupyter lab      : 1.2.6
nbconvert        : 5.6.1
ipywidgets       : not installed
nbformat         : 5.0.4
traitlets        : 4.3.3

3. jupyter_notebook_config.jsonに設定追加

{
  "LanguageServerManager": {
    "language_servers": {
      "python": {
        "version": 1,
        "argv": ["python", "-m", "pyls"],
        "languages": ["python"]
      }
    }
  }
}

起動

$jupyter lab
# ...

ちゃんと出ました。便利。

f:id:arata3da4:20200221125607p:plain
Python3の補完

参考

qiita.com