Movatterモバイル変換


[0]ホーム

URL:


メインコンテンツに移動
インプレス ビジネスメディア

はじめに

これまで、MySQLで点、線、面の情報を扱う方法を解説してきました。地理情報専用のデータ型であるジオメトリー型に登録する際に、WKTでPOINT、LINESTRING、POLYGONのキーワードを使うのでしたね。

点のデータは専用型に入れる必要がある?

線や面のデータを地理情報専用の型を使わないで格納するのはちょっと大変そうですが、点のデータについては、わざわざ専用のPOINT型を使わなくても、緯度と経度の値をそれぞれそのまま数値として格納すれば良いのではないか、という発想もあると思います。個人的には特に理由がない限り、専用の型を使っておけば良いと考えています。その理由として、

  • 明らかにおかしな値を登録した場合(緯度で90度、経度で180度を超えるような値)にエラーで弾いてくれる
  • 測地系の情報を一緒に管理できる
  • 2点間の距離やポリゴン等との包含関係の算出などで、地理情報型になっていればそのまま演算に使える

といったものがあります。

一方で、元のCSVデータなどで緯度と経度の数値が入っていてそのまま登録したかったり、上で挙げたような利点は特に活用する必要がないといった場合など、緯度カラムと経度カラムで値を管理したいことも理解できます。今回はそのようなデータの扱い方について紹介します。

データの用意

緯度と経度をそれぞれDOUBLE型の数値として持つテーブルを作成します。今回のテーブルではGEOMETRY型は使用しません。「lat」が緯度(「latitude」の略)、「lon」が経度(「longitude」の略)です。

CREATE TABLE g12(id integer, name varchar(30), lat double, lon double);

2つほど点の位置情報を登録してみましょう。サンプルデータは北緯35度ちょうど東経135度ちょうどにある「日本のへそ」という場所と、北緯35.694572度、東経139.760397度にあるインプレスの場所です。

INSERT INTO g12 VALUES (1, '日本のへそ', 35, 135);INSERT INTO g12 VALUES (2, 'インプレス', 35.694572, 139.760397);

登録された情報を確認すると以下のようになります。文字列や数値からなる、よく見るテーブルデータですね。

mysql> SELECT * FROM g12;+------+-----------------+-----------+------------+| id   | name            | lat       | lon        |+------+-----------------+-----------+------------+|    1 | 日本のへそ      |        35 |        135 ||    2 | インプレス      | 35.694572 | 139.760397 |+------+-----------------+-----------+------------+2 rows in set (0.000 sec)

地理情報型への変換

これらのデータを地理情報の関数で使用したい場合は、地理情報型に変換する必要があります。基本的には前回までに紹介した「ST_GeomFromText()関数にWKTを与える」という考え方です。WKTの部分をlat列、lon列の値から作り込むことになります。

mysql> SELECT id, name, lat, lon, ST_GeomFromText(CONCAT('POINT(',lat,' ',lon,')'),6668) pos FROM g12;+------+-----------------+-----------+------------+------------------------------------------------------+| id   | name            | lat       | lon        | pos                                                  |+------+-----------------+-----------+------------+------------------------------------------------------+|    1 | 日本のへそ      |        35 |        135 | 0x0C1A000001010000000000000000E060400000000000804140 ||    2 | インプレス      | 35.694572 | 139.760397 | 0x0C1A0000010100000040DF162C55786140D15B3CBCE7D84140 |+------+-----------------+-----------+------------+------------------------------------------------------+2 rows in set (0.000 sec)

今回の例では、それぞれの点データに対するデータベースはSRIDの情報を持っていないので、SQL文を書く人が「知っている」ことが前提となる点に気をつけてください(これが私が地理情報専用型の使用を勧める最大の理由です)。より安全で確実なデータ管理の観点からはlat、lonとは別にsrid列を作って全ての列にSRIDの値を登録するのもありかもしれませんし、このシステム全体で使うSRIDの情報を管理するためだけのテーブルを1つ作るのも方法かもしれません。

例で示したSQLは複雑に見えますが、ST_GeomFromText()関数の引数としてCONCATで作ったWKT(POINT)文字列とSRIDの数値を渡しているだけであることが分かると思います。

POINT関数を使う場合は

MySQLのマニュアルを見た人の中には、POINT()という関数を目ざとく見つけた人がいるかもしれません。今回の格納データで使用できるのではないでしょうか。見てみましょう。

mysql> SELECT id, name, lat, lon, POINT(lat,lon) pos FROM g12;+------+-----------------+-----------+------------+------------------------------------------------------+| id   | name            | lat       | lon        | pos                                                  |+------+-----------------+-----------+------------+------------------------------------------------------+|    1 | 日本のへそ      |        35 |        135 | 0x00000000010100000000000000008041400000000000E06040 ||    2 | インプレス      | 35.694572 | 139.760397 | 0x000000000101000000D15B3CBCE7D8414040DF162C55786140 |+------+-----------------+-----------+------------+------------------------------------------------------+2 rows in set (0.000 sec)

先ほどのCONCATを使った例に比べ、SQLは非常にシンプルになっています。しかし、登録されたデータをよく見比べてみると、先ほどとは異なっていることに気がつきます。主な相違点としては

  • SRID部分(最初の4バイト)がゼロになっている
  • 緯度と経度が逆の順で登録されている

という点が挙げられます。測地系の情報というのは「これはJGD2011(SRID:6668)で表された座標です」といったことを表すものですから、その値がゼロであることは単なる平面座標(デカルト座標)上での座標を示したことになり、正しい地球上での位置を指していません。これでは使えません。

そこでSRIDをセットする関数の登場です。「ST_SRID」という関数を使います。

SELECT id, name, lat, lon, ST_SRID(POINT(lon,lat),6668) pos FROM g12;mysql> SELECT id, name, lat, lon, ST_SRID(POINT(lon,lat),6668) pos FROM g12;+------+-----------------+-----------+------------+------------------------------------------------------+| id   | name            | lat       | lon        | pos                                                  |+------+-----------------+-----------+------------+------------------------------------------------------+|    1 | 日本のへそ      |        35 |        135 | 0x0C1A000001010000000000000000E060400000000000804140 ||    2 | インプレス      | 35.694572 | 139.760397 | 0x0C1A0000010100000040DF162C55786140D15B3CBCE7D84140 |+------+-----------------+-----------+------------+------------------------------------------------------+2 rows in set (0.000 sec)

先ほどのPOINT()関数の結果にST_SRID()関数で測地系を与えることで、正しくJGD2011(SRID:6668)のデータになったことが確認できました(ST_GeomFromText()のときの結果と見比べてみてください)。

このように、POINT関数とST_SRID関数を組み合わせることでST_GeomFromText関数のときと同じようなことができます。しかし、例えばPOINT関数だけを使用してSRIDの設定を忘れてしまう「うっかり事故」を起こしてしまったり、緯度と経度の指定方法が他と逆順だったりなど、事故につながる可能性が大きいため、地理情報を扱う際には基本的にST_が先頭に付く関数を使用することを心がけるよう、お勧めします。

【コラム】大津駅の北緯35度モニュメント

本文で取り上げた「日本のへそ」(北緯35度・東経135度)にあるモニュメントは第5回で紹介しましたが、これ以外にも緯度や経度のキリ番のモニュメントは様々な場所にあります。今回紹介するのは、滋賀県大津駅のホームにある北緯35度線を示すモニュメントです。

奥に見える水色の球体がモニュメントです。駅名表示板には隣の駅として小説「成瀬」シリーズで有名になった「膳所(ぜぜ)」の文字が見えます。

近づいてみると、上面をオレンジ色に塗装したレールによって、北緯35度の線を表しているのを見ることができます。

解説板です。1989年に設置されたとのことで、明らかにTokyo測地系であると判断できます。現在のJGD2011による北緯35度は、ここよりも360mほど南を通っています。

JRの駅は少し琵琶湖から離れていますが、せっかくなので琵琶湖まで歩いてみました。そこには「成瀬」シリーズで有名になった「ミシガン」とご対面できました!

この記事のキーワード

この記事をシェアしてください

この記事の筆者

坂井 恵 (さかい けい)

有限会社アートライ 代表取締役

MySQLや地理情報系などのコミュニティ活動を通して様々な情報に触れるのが好き。データベースについては、業務や世の中の流れが見える「データそのもの」や「その変化」に強い関心を持っているが、最近はPG-Stromのプロジェクトに参加したこともあり、改めて性能評価への関心も高まっている。

業界情報やナレッジが詰まったメルマガやソーシャルぜひご覧ください

Think ITでは、技術情報が詰まったメールマガジン「Think IT Weekly」の配信サービスを提供しています。メルマガ会員登録を済ませれば、メルマガだけでなく、さまざまな限定特典を入手できるようになります。

Follow us on Google news

人気記事トップ10

「MySQL」と「PostgreSQL」の「データの暗号化」機能を比較する【arXiv最前線】自律型AIに潜む「信頼できない思考プロセス」「jQuery」でWebゲーム「Color」を開発してみよう【ソフトウエアエンジニア編】“伝えたつもり”が実は伝わっていない問題の回避策「緯度」「経度」をMySQLに数値で登録しておきたいときの対処法KDE、デスクトップ環境「KDE Plasma 6.6.0」リリース ─ UI改善とアクセシビリティ強化社会実装に踏み出す1歩を、ここからー「NEMTUS Hackathon HACK+2026」開催中! テキストエディタ「Vim 9.2」リリース ─ Vim9言語の強化やdiffモード改善など大幅なアップデート デスクトップ向けLinuxディストリビューション「Sparky 8.2」リリース ─ 「Debian 13」ベースLinuxディストリのポイントリリースGentoo、Codebergに公式ミラーを開設 ─ Gitホスティング体制を拡張
LLMの「親切さ」を逆手に取るジェイルブレイク手法「HILL」と防御の限界【ソフトウエアエンジニア編】“伝えたつもり”が実は伝わっていない問題の回避策 テキストエディタ「Vim 9.2」リリース ─ Vim9言語の強化やdiffモード改善など大幅なアップデート「jQuery」でWebゲーム「Color」を開発してみよう【arXiv最前線】自律型AIに潜む「信頼できない思考プロセス」「MySQL」と「PostgreSQL」の「データの暗号化」機能を比較する【号外:後編】中学生起業家からトヨタ部長までが共演。350名が目撃した「生成AIギルド大感謝祭」全貌レポートGitHub Universe 2025、日本からの参加者による座談会を開催Metaとユタ大学がリストバンド型デバイスを共同研究ほかネットワーク管理ツール「NetworkManager 1.56」リリース ─ 安定性と接続管理機能を強化
LLMの「親切さ」を逆手に取るジェイルブレイク手法「HILL」と防御の限界【ソフトウエアエンジニア編】“伝えたつもり”が実は伝わっていない問題の回避策GitHub Universe 2025、日本からの参加者による座談会を開催Valveが新型ハードウェアを2026年上半期に出荷ほか【号外:後編】中学生起業家からトヨタ部長までが共演。350名が目撃した「生成AIギルド大感謝祭」全貌レポート テキストエディタ「Vim 9.2」リリース ─ Vim9言語の強化やdiffモード改善など大幅なアップデートLinuxカーネル「Linux 6.19」リリース ─ 次期リリースは「7.0」に「jQuery」でWebゲーム「Color」を開発してみようオープンソースの圧縮・解凍ソフト「PeaZip 10.9.0」リリース ─ GUI強化と多形式プレビュー対応で利便性向上Gateway API(「kgateway」+「agentgateway」)でKubernetes上のAIツール接続を制御する
人気記事ランキングをもっと見る

企画広告も役立つ情報バッチリ!Sponsored

【CNDW2025】Grafanaが明かす「オブザーバビリティの哲学」ー最小限の労力で実用的なインサイトを得るには1月23日 6:30【CNDW2025】プロダクト急増に備える基盤刷新 ーウェルスナビがECSからEKSへの移行で得た知見とは1月15日 6:30【CNDW2025】250環境を5人で運用、構築時間は30分に ーKINTOテクノロジーズが語るインフラ基盤組織の作り方2025年12月18日 6:30新たな自動化で熱視線! AIエージェントの「推論能力」を支える2つのコンポーネントとは?2025年11月28日 6:30IoTに生成AIを掛け合わせる「AI-driven IoT」で現場のIoTデータ活用を加速2025年11月26日 6:30アイレット、KDDIの属人化問題を生成AIアシスタントの精度を高め解消へ2025年11月21日 6:30「Grafana Cloud」の先進的ユーザーであるグリーが10年をかけて到達した「オブザーバービリティ」とは2025年5月15日 6:30Grafana Labs CTOのTom Wilkie氏インタビュー。スクラップアンドビルドから産まれた「トラブルシューティングの民主化」とは2025年4月21日 6:30API管理をより簡単にする「Kong Konnect」が解決する課題とその主要機能2025年3月5日 5:30目指すはプロセス連結によるサイロ化の打破! ガバナンス強化にも寄与する自動化プラットフォームとは2025年1月15日 6:30

[8]ページ先頭

©2009-2026 Movatter.jp