日本語 文章 文法 チェッカー
https://so-zou.jp/web-app/text/proofreading/

江端智一のホームページ
まだ問題山積だけど、golangのCSVパースが通った。
package main
import (
"encoding/csv"
"encoding/json"
"fmt"
"strings"
)
type Location struct {
Lat float64 `json:"lat"`
Lng float64 `json:"lng"`
}
type Record struct {
ID int `json:"id"`
UserID int `json:"user_id"`
Distance float64 `json:"distance"`
Place []Location `json:"place"`
Speed []float64 `json:"speed"`
Prediction int `json:"prediction_type"`
StartAt string `json:"start_at"`
EndAt string `json:"end_at"`
}
func main() {
// 提供されたCSVデータ
csvData := `50,7,53.04935656638487,"[{""lat"": 34.6653, ""lng"": 135.2241}, {""lat"": 34.6653, ""lng"": 135.2241}, {""lat"": 34.6652, ""lng"": 135.2241}, {""lat"": 34.6652, ""lng"": 135.224}, {""lat"": 34.6651, ""lng"": 135.224}, {""lat"": 34.665, ""lng"": 135.224}, {""lat"": 34.6649, ""lng"": 135.2239}]","[0.0, 0.0001, 0.0002, 0.0002, 0.0004, 0.0004, 0.0004]",1,2023-03-03 07:40:00,2023-03-03 07:43:00`
// CSVデータを読み込む
r := csv.NewReader(strings.NewReader(csvData))
record, err := r.Read()
if err != nil {
fmt.Println("CSVデータを読み込めません:", err)
return
}
// CSVデータをパース
id := record[0]
userID := record[1]
distance := record[2]
placeJSON := record[3]
speedJSON := record[4]
prediction := record[5]
startAt := record[6]
endAt := record[7]
// JSONデータをパース
var place []Location
if err := json.Unmarshal([]byte(placeJSON), &place); err != nil {
fmt.Println("Placeデータをパースできません:", err)
return
}
var speed []float64
if err := json.Unmarshal([]byte(speedJSON), &speed); err != nil {
fmt.Println("Speedデータをパースできません:", err)
return
}
// パースしたデータを表示
fmt.Println("ID:", id)
fmt.Println("User ID:", userID)
fmt.Println("Distance:", distance)
fmt.Println("Place:", place)
// Placeを要素単位で表示
fmt.Println("Place:")
for _, loc := range place {
fmt.Printf("Lat: %.4f, Lng: %.4f\n", loc.Lat, loc.Lng)
}
fmt.Println("Speed:", speed)
// Speedを要素単位で表示
fmt.Println("\nSpeed:")
for i, s := range speed {
fmt.Printf("Index %d: %.4f\n", i, s)
}
fmt.Println("Prediction Type:", prediction)
fmt.Println("Start At:", startAt)
fmt.Println("End At:", endAt)
}
出力結果
ID: 50
User ID: 7
Distance: 53.04935656638487
Place: [{34.6653 135.2241} {34.6653 135.2241} {34.6652 135.2241} {34.6652 135.224} {34.6651 135.224} {34.665 135.224} {34.6649 135.2239}]
Place:
Lat: 34.6653, Lng: 135.2241
Lat: 34.6653, Lng: 135.2241
Lat: 34.6652, Lng: 135.2241
Lat: 34.6652, Lng: 135.2240
Lat: 34.6651, Lng: 135.2240
Lat: 34.6650, Lng: 135.2240
Lat: 34.6649, Lng: 135.2239
Speed: [0 0.0001 0.0002 0.0002 0.0004 0.0004 0.0004]Speed:
Index 0: 0.0000
Index 1: 0.0001
Index 2: 0.0002
Index 3: 0.0002
Index 4: 0.0004
Index 5: 0.0004
Index 6: 0.0004
Prediction Type: 1
Start At: 2023-03-03 07:40:00
End At: 2023-03-03 07:43:00
CREATE TABLE trips_test (
id serial PRIMARY KEY,
user_id integer,
distance double precision,
place point[],
speed double precision[],
prediction_type integer,
start_at timestamp,
end_at timestamp
);
INSERT INTO trips_test (user_id, distance, place) VALUES (1, 24.66249845798845, ARRAY[point '(34.7241, 135.1294)', point '(34.7241, 135.1294)', point '(34.7241, 135.1294)']);
moove=# INSERT INTO trips_test (user_id, distance, place)
moove-# VALUES (1, 24.66249845798845, ARRAY[point '(34.7241, 135.1294)', point '(34.7241, 135.1294)', point '(34.7241, 135.1294)']);
INSERT 0 1
moove=# select * from trips_test;
id | user_id | distance | place | speed | prediction_type | start_at | end_at
----+---------+-------------------+------------------------------------------------------------------+-------+-----------------+----------+--------
1 | 1 | 24.66249845798845 | {"(34.7241,135.1294)","(34.7241,135.1294)","(34.7241,135.1294)"} | | | |
(1 row)
上記のテーブルから、座標情報を一つ一つ取り出すにはどうしたら良いですか
SELECT id, user_id, unnest(place) AS single_point
FROM trips_test;
moove=# SELECT id, user_id, unnest(place) AS single_point
moove-# FROM trips_test;
id | user_id | single_point
----+---------+--------------------
1 | 1 | (34.7241,135.1294)
1 | 1 | (34.7241,135.1294)
1 | 1 | (34.7241,135.1294)
を参考にして頂きつつ、インストール実施中。
私は、根拠なく、
$ sudo apt-get install docker-ce=5:24.0.4-1~ubuntu.22.04~jammy
を選びました。
ラズパイ4、Ubuntu22.04、で"docker compose"も動いているようです ーー "docker-compose"は動きません。
-- カスタムプロトコルの識別子(任意の値を設定)
local NX_PROTOCOL = Proto("NXDlink", "nxdlink protocol dissector")
-- プロトコルのフィールド定義
local nx_protocol_fields = NX_PROTOCOL.fields
nx_protocol_fields.magic = ProtoField.string("nx_protocol.magic", "Magic Number")
nx_protocol_fields.message_length = ProtoField.uint32("nx_protocol.message_length", "Message Length")
nx_protocol_fields.source_address = ProtoField.uint32("nx_protocol.source_address", "Source Address")
nx_protocol_fields.destination_address = ProtoField.uint32("nx_protocol.destination_address", "Destination Address")
nx_protocol_fields.timestamp = ProtoField.uint32("nx_protocol.timestamp", "Timestamp")
nx_protocol_fields.message_number = ProtoField.uint32("nx_protocol.message_number", "Message Number")
nx_protocol_fields.m_ctl = ProtoField.uint32("nx_protocol.m_ctl", "M_CTL")
nx_protocol_fields.inq_id = ProtoField.string("nx_protocol.inq_id", "INQ_ID")
nx_protocol_fields.tcd = ProtoField.uint32("nx_protocol.tcd", "TCD")
nx_protocol_fields.ver = ProtoField.uint32("nx_protocol.ver", "VER")
nx_protocol_fields.gtid = ProtoField.string("nx_protocol.gtid", "GTID")
nx_protocol_fields.mode = ProtoField.uint32("nx_protocol.mode", "MODE")
nx_protocol_fields.pver = ProtoField.uint32("nx_protocol.pver", "PVER")
nx_protocol_fields.pri = ProtoField.uint32("nx_protocol.pri", "PRI")
nx_protocol_fields.cbn = ProtoField.uint32("nx_protocol.cbn", "CBN")
nx_protocol_fields.tbn = ProtoField.uint32("nx_protocol.tbn", "TBN")
nx_protocol_fields.bsize = ProtoField.uint32("nx_protocol.bsize", "BSIZE")
nx_protocol_fields.fui = ProtoField.uint32("nx_protocol.fui", "FUI")
-- nx_protocol_fields.fc = ProtoField.uint32("nx_protocol.fc", "FC", base.HEX)
nx_protocol_fields.fc = ProtoField.uint32("nx_protocol.fc", "FC")
nx_protocol_fields.field_x = ProtoField.uint32("nx_protocol.field_x", "FIELD_X")
nx_protocol_fields.field_y = ProtoField.uint32("nx_protocol.field_y", "FIELD_Y")
nx_protocol_fields.field_z = ProtoField.uint32("nx_protocol.field_z", "FIELD_Z")
-- カスタムプロトコルの識別子(任意の値を設定)
--local DATA_PROTOCOL = Proto("DATALink", "datalink protocol dissector")
-- プロトコルのフィールド定義
--local data_protocol_fields = DATA_PROTOCOL.fields
--data_protocol_fields.fc = ProtoField.uint32("data_protocol.fc", "FC")
-- パケット解析関数
function NX_PROTOCOL.dissector(buffer, pinfo, tree)
-- フレーム情報を表示
pinfo.cols.protocol:set("NX Protocol")
local subtree = tree:add(NX_PROTOCOL, buffer(), "NX Protocol Data")
-- "NUXM" ヘッダ文字列を確認
local data = buffer():string()
-- local offset = data:find("NUXM")
local offset = data:find("NUXM") -1 -- 1を引かないと、ずれる
if not offset then
-- "NUXM" が見つからない場合は解析を中止
return
end
-- ヘッダ情報を解析
subtree:add(nx_protocol_fields.magic, buffer(offset, 4))
subtree:add(nx_protocol_fields.message_length, buffer(offset + 4, 4))
subtree:add(nx_protocol_fields.source_address, buffer(offset + 8, 4))
subtree:add(nx_protocol_fields.destination_address, buffer(offset + 12, 4))
subtree:add(nx_protocol_fields.timestamp, buffer(offset + 16, 4))
subtree:add(nx_protocol_fields.message_number, buffer(offset + 20, 4))
subtree:add(nx_protocol_fields.m_ctl, buffer(offset + 24, 4))
subtree:add(nx_protocol_fields.inq_id, buffer(offset + 28, 12))
subtree:add(nx_protocol_fields.tcd, buffer(offset + 40, 2))
subtree:add(nx_protocol_fields.ver, buffer(offset + 42, 2))
subtree:add(nx_protocol_fields.gtid, buffer(offset + 44, 8))
subtree:add(nx_protocol_fields.mode, buffer(offset + 52, 2))
subtree:add(nx_protocol_fields.pver, buffer(offset + 54, 1))
subtree:add(nx_protocol_fields.pri, buffer(offset + 55, 1))
subtree:add(nx_protocol_fields.cbn, buffer(offset + 56, 1))
subtree:add(nx_protocol_fields.tbn, buffer(offset + 57, 1))
subtree:add(nx_protocol_fields.fui, buffer(offset + 60, 4))
subtree:add(nx_protocol_fields.fc, buffer(offset + 64, 2))
-- fcの値を取得
-- local fc_value = buffer(offset + 64, 2):le_uint() -- リトルエンディアンの場合
local fc_value = buffer(offset + 64, 2)-- リトルエンディアンの場合
-- デバッグ情報を表示
-- print("fc_value:", string.format("0x%04X", fc_value)) -- 16進数表示
-- fcの値に応じてフィールドを追加
-- if fc_value == 0x181 then
-- if fc_value == 385 then
if fc_value = 0 then
-- 0x181の場合、特定のフィールドを追加
subtree:add(nx_protocol_fields.field_x, buffer(offset + 66, 4))
elseif fc_value == 0x183 then
-- 0x183の場合、別のフィールドを追加
subtree:add(nx_protocol_fields.field_y, buffer(offset + 66, 4))
elseif fc_value == 0x188 or fc_value == 0x189 then
-- 0x188または0x189の場合、共通のフィールドを追加
subtree:add(nx_protocol_fields.field_z, buffer(offset + 66, 4))
else
-- その他の場合、何もしない
end
end
--function DATA_PROTOCOL.dissector(buffer, pinfo, tree)
-- フレーム情報を表示
-- pinfo.cols.protocol:set("DATA Protocol")
-- local subtree = tree:add(DATA_PROTOCOL, buffer(), "DATA Protocol Data")
-- subtree:add(data_protocol_fields.fc, buffer(64, 2))
--end
-- プロトコルをWiresharkに登録
local udp_table = DissectorTable.get("udp.port")
udp_table:add(10631, NX_PROTOCOL) -- UDPポート10631でカスタムプロトコルを解析
udp_table:add(40311, NX_PROTOCOL) -- UDPポート40311でカスタムプロトコルを解析
udp_table:add(40312, NX_PROTOCOL) -- UDPポート40312でカスタムプロトコルを解析
ラプラス分布は、ランデル分布とも言われて、交通工学のシミュレーションでは非常に重要な確率分布として使われているようです。

パラメータとして、平均(location parameter)を表す μ と尺度(scale parameter)を表すbを持ち、ラプラス分布の確率密度関数は、 f(x∣μ,b)=1/2b exp(−b∣x−μ∣) と表される。
でもって、
交通シミュレーションで使われる場面
■交通の到着間隔のモデリング → 乗客の到着間隔をモデル化するため
■トラフィックの所要時間の予測 → 自動車の移動時間やトラフィックの所要時間を予測するため
■信号制御の最適化 → 信号のサイクルタイムやフェーズの最適化を行うため
■交通事故の発生確率の評価 → 交通事故の発生確率を評価するため
と、まあ、ここまでは分かったのですが、この分布の数学的な意義が分かりません。(正規分布や指数分布などは、理解できていると思います)
未来を占う人工知能 ~人類が生み出した至宝の測定ツールhttps://t.co/fno5ZpjWTu pic.twitter.com/hjSbummE9r
— EE Times Japan編集部 (@eetimes_jp) January 31, 2018
ですが、ラプラス分布の数学的な意義が分かりません。
で、以下のように推察しているのですが、私のこの推察は正しいでしょうか?
ラプラス分布を使う理由(江端の私見)
■外れ値のモデル化の為
→ そもそも、バスの到着時間が、正規分布のように曖昧に分散していたらとても困る。情報通信についても同様。とは言え、外れ値を完全に無視することはできない。そこで、このような、交通、情報を扱う分布として、(積分して1になる関数として)便利なツールとして、ラプラス分布が使われている
どなたか、ご見解を頂ければ幸いです。
江端
Golangで、以下のXML分の中から、<tag k="route" v="bus"/>を発見した時に、refの要素を参照にして位置情報を取り出すプログラムを書いて
<osm>
<node id="2197214759" lat="35.5714149" lon="139.5880043" version="1" timestamp="2013-03-12T09:31:19Z" changeset="15336763" uid="1258339" user="k___0e0">
<tag k="highway" v="bus_stop"/>
<tag k="name" v="有馬第二団地前"/>
</node>
<node id="2197214762" lat="35.5715628" lon="139.5875429" version="1" timestamp="2013-03-12T09:31:19Z" changeset="15336763" uid="1258339" user="k___0e0">
<tag k="highway" v="bus_stop"/>
<tag k="name" v="有馬第二団地前"/>
</node>
<relation id="2814953" version="38" timestamp="2023-06-14T08:20:58Z" changeset="137316398" uid="1687166" user="U20">
<member type="node" ref="2197214759" role="backward_stop"/>
<member type="node" ref="2197214762" role="forward_stop"/>
<tag k="route" v="bus"/>
</relation>
</osm>
ChatGPTの回答
指定されたXMLデータから を検出し、それに対応する ref 要素を参照にして位置情報を取得するGolangのプログラムを以下に示します。このプログラムは、encoding/xml パッケージを使用してXMLを解析します。
package main
import (
"encoding/xml"
"fmt"
"log"
"strings"
)
type OSM struct {
XMLName xml.Name `xml:"osm"`
Nodes []Node `xml:"node"`
Relations []Relation `xml:"relation"`
}
type Node struct {
ID int64 `xml:"id,attr"`
Lat float64 `xml:"lat,attr"`
Lon float64 `xml:"lon,attr"`
Tags []Tag `xml:"tag"`
}
type Relation struct {
ID int64 `xml:"id,attr"`
Members []Member `xml:"member"`
Tags []Tag `xml:"tag"`
}
type Member struct {
Type string `xml:"type,attr"`
Ref string `xml:"ref,attr"`
Role string `xml:"role,attr"`
}
type Tag struct {
K string `xml:"k,attr"`
V string `xml:"v,attr"`
}
func main() {
xmlData := `
<osm>
<node id="2197214759" lat="35.5714149" lon="139.5880043" version="1" timestamp="2013-03-12T09:31:19Z" changeset="15336763" uid="1258339" user="k___0e0">
<tag k="highway" v="bus_stop"/>
<tag k="name" v="有馬第二団地前"/>
</node>
<node id="2197214762" lat="35.5715628" lon="139.5875429" version="1" timestamp="2013-03-12T09:31:19Z" changeset="15336763" uid="1258339" user="k___0e0">
<tag k="highway" v="bus_stop"/>
<tag k="name" v="有馬第二団地前"/>
</node>
<relation id="2814953" version="38" timestamp="2023-06-14T08:20:58Z" changeset="137316398" uid="1687166" user="U20">
<member type="node" ref="2197214759" role="backward_stop"/>
<member type="node" ref="2197214762" role="forward_stop"/>
<tag k="route" v="bus"/>
</relation>
</osm>
`
var osmData OSM
err := xml.Unmarshal([]byte(xmlData), &osmData)
if err != nil {
log.Fatal(err)
}
for _, relation := range osmData.Relations {
for _, tag := range relation.Tags {
if tag.K == "route" && tag.V == "bus" {
for _, member := range relation.Members {
if member.Type == "node" {
node := getNodeByID(member.Ref, osmData.Nodes)
if node != nil {
fmt.Printf("Bus Stop: %s\n", getNodeName(node))
fmt.Printf("Coordinates: Lat %f, Lon %f\n\n", node.Lat, node.Lon)
}
}
}
}
}
}
}
func getNodeByID(ref string, nodes []Node) *Node {
for _, node := range nodes {
if fmt.Sprintf("%d", node.ID) == ref {
return &node
}
}
return nil
}
func getNodeName(node *Node) string {
for _, tag := range node.Tags {
if tag.K == "name" {
return tag.V
}
}
return ""
}
このプログラムは、与えられたXMLデータから を見つけ、それに関連する ref 要素を参照してバス停の位置情報を取得して表示します。XMLデータは xmlData 変数に直接格納されていますが、実際のプログラムではファイルから読み込むこともできます。コード内のコメントに従って、XMLデータ構造やタグを調整してください。
世界が変わる
生成AIを使わない奴は、"死ぬ" ―― 文字通りの意味で。
>osm2pgrouting -f tsuzuki.osm -c mapconfig_for_cars_rail.xml -d tsuzuki_rail -U postgres -h 192.168.0.23 -p 15432 -W password
<?xml version="1.0" encoding="UTF-8"?>
<configuration>
<tag_name name="highway" id="1">
<tag_value name="motorway" id="101" priority="1.0" maxspeed="130" />
<tag_value name="motorway_link" id="102" priority="1.0" maxspeed="130" />
<tag_value name="motorway_junction" id="103" priority="1.0" maxspeed="130" />
<tag_value name="trunk" id="104" priority="1.05" maxspeed="110" />
<tag_value name="trunk_link" id="105" priority="1.05" maxspeed="110" />
<tag_value name="primary" id="106" priority="1.15" maxspeed="90" />
<tag_value name="primary_link" id="107" priority="1.15" maxspeed="90" />
<tag_value name="secondary" id="108" priority="1.5" maxspeed="90" />
<tag_value name="secondary_link" id="109" priority="1.5" maxspeed="90"/>
<tag_value name="tertiary" id="110" priority="1.75" maxspeed="90" />
<tag_value name="tertiary_link" id="111" priority="1.75" maxspeed="90" />
<tag_value name="residential" id="112" priority="2.5" maxspeed="50" />
<tag_value name="living_street" id="113" priority="3" maxspeed="20" />
<tag_value name="service" id="114" priority="2.5" maxspeed="50" />
<tag_value name="unclassified" id="117" priority="3" maxspeed="90"/>
<tag_value name="road" id="100" priority="5" maxspeed="50" />
</tag_name>
<tag_name name="railway" id="1">
<tag_value name="subway" id="101" priority="1.0" maxspeed="40" />
<tag_value name="rail" id="101" priority="1.0" maxspeed="40" />
</tag_name>
</configuration>
とりあえず、ちゃんと、JRと市営地下鉄が加えられている。

この後は、osmファイルを手作業で加工
がんばれ > 自分