web-dev-qa-db-ja.com

国際的な地理的住所をリレーショナルデータベースにどのように保存する必要がありますか?

国際的な地理的住所をリレーショナルテーブルに格納するタスクを考えると、最も柔軟なスキーマは何ですか?住所のすべての部分を独自のフィールドに分割する必要がありますか、それともフリーテキストのようにする必要がありますか?

異なる形式のアドレスを異なるテーブルに分ける意味はありますか?たとえば、USAAddress、CanadianAddress、UKAddress ...のテーブルがありますか?

55
Bob

私のブログ記事から私の考えを要約します- アドレスストレージのレッスン

現在のプロジェクト[私は物流会社で働いています]では、国際住所を保存しています。データベースのこの部分の設計では、世界中の住所に関する調査を行ってきました。さまざまな形式がたくさんあります。西洋の世界では、かなり統一された形式を使用する傾向があります-いくつかの違いはありますが、ほとんどは次のとおりです。

  • 番地-数値
  • 家または建物の名前-[VarChar-一部の家/建物は、番号ではなく名前で識別されます]
  • Street Number Suffix[VarChar、ほとんどの場合、Char(1)で十分です]
    • A、Bなど
  • 通りの名前[VarChar]
  • Street Type[StreetTypesテーブルがある場合は、VarCharまたはInt]
    • これまでのところ、私は英語圏で262のユニークなタイプを見つけましたが、おそらくもっと多くあり、他の言語、つまりStrasse、Rueなどを忘れないでください。
  • 通りの方向[VarChar(2)]
    • N、E、S、W、NE、SE、NW、SW
  • Address Type[VarCharまたはInt(AddressTypesテーブルがある場合)]
    • 私書箱
    • アパート
    • 建物
    • オフィス
    • Suite
    • 等...
  • Address Type Identifier[VarChar]
    • つまり、ボックス番号、アパートメント番号、フロア番号は、アパートメント番号を覚えており、オフィスには1Aのような英数字の情報が含まれていることがあります。
  • Local Municipality[Municipalitiesテーブルがある場合は、VarCharまたはInt]
    • たとえば、あなたの集落/村が町の前の住所に表示されている場合。
  • City/Town[Citiesテーブルがある場合は、VarCharまたはInt]
  • 統治地区[地区テーブルがある場合は、VarCharまたはInt]
    • 州(米国)
    • 州(カナダ)
    • 連邦管区(メキシコ)
    • 郡(イギリス)
    • 等...
  • 郵便エリア[VarChar]
    • 郵便番号(米国)
    • 郵便番号(カナダ、メキシコ)
    • 郵便番号(英国)
  • Country[国テーブルがある場合は、VarCharまたはInt]

これはほとんどの国をカバーしているようですが、フィールドの順序が異なる場合があります。表示形式のリストは http://www.bitboost.com/ref/international-address-formats.html#Formats にあります。

たとえば、多くの国では、郵便番号は都市名の前にあり、番地は通り名の後にあります。カナダ、米国、英国では、番地は番地の前にあり、郵便番号(または郵便番号)は市名の後にあります。

住所を異なる国に分離することについてのあなたの質問に答えて、私はそれをお勧めしません。それは他の分野、例えば報告などで生活を困難にするだけです。私が提供した形式は、米国、カナダ、メキシコ、英国を問題なくカバーするロジスティクスデータベースのすべての住所をカバーしています。また、ヨーロッパ、中国、日本、マレーシアのすべての住所をカバーしています。他の国では話せませんが、これらのフィールドでサポートされない国の住所を保存する必要はありません。

他の人が提案し、多くのデータベースで見られるAddress1、Address2、Address3形式を使用することはお勧めしません。特に、データが正しく入力されていない場合、英数字文字列からのアドレス情報の解析は最初に思われるほど簡単ではないためです。 、誤った情報、タイプミス、スペルミスなどが原因で発生します。フィールドを区切る場合は、距離アルゴリズムを使用して可能性のある意味を確認したり、確率を使用して通りの名前を郵便番号や通り番号と照合したり、州や都市を通りの名前と照合したりできます。住所全体を表す文字列を取得したら、そのいずれかを行います。想像力を伸ばしても、それは些細なことではありません。

アドレスデータベースのQAは頭痛の種です。この領域での生活を簡素化する最も簡単な方法は、すべてのフィールドに、入力時に正しいと自動的に検証できる単一の情報のみが保持されるようにすることです。確率、距離アルゴリズム、および正規表現は、入力の有効性をチェックし、ユーザーの間違いについてフィードバックをユーザーに提供し、適切な修正を提案できます。

注意すべき1つの注意点は、通りのタイプでもある名前の付いた道路です。カナダをカバーしている場合は、トロントの「アベニューロード」に注意する必要があります。 、3フォーマット。これは他の場所でも発生する可能性がありますが、私はそれらを認識していません-この単一のインスタンスは、WTFを叫ぶのに十分でしたか?!

88
BenAlabaster

アドレス形式を過度に分析しないように注意してください。これを行うと、ほとんどのユーザーがaroundで作業し、間違ったフィールドを使用するように強制する必要がある仕様になってしまう可能性が高くなります。または、プライマリフィールドのみを入力し、余分なフィールドは無視します。

物事をシンプルに保つ。

BenAlabasterで言及されているようなStreetTypeは、英語やスペイン語などの分離言語とは異なる言語で作業を開始すると問題を引き起こします。

どのように悪いことが自然に起こり得るかを示すために:「ヘンリエット」+「ローランドホルスト」+「ストレート」から構築された、アムステルダムの「ヘンリエットローランドホルスト通り」。「ローランドホルスト通り」または「 Roland Holststr。」、または「HRHolststr」のスペルを間違えた。天候によっては、「ヘンリエットローランドホルスト通り」。地球上の各国の最新のストリートレジスタがない限り、どこにも行きません。

そして最後に、一部の多言語の国では、名前が言語によって異なる可能性があることに注意してください!たとえば、ブリュッセルでは、多くの街路にフランス語のandオランダ語の名前があります:宛先の優先言語に応じて、「Avenu du Port」と「Havenlaan」。 (Googleマップでは、念のため、両方の名前を交互に表示しています。)

ここであらゆる種類の巧妙なトリックを考案することができますが、営業担当です。これを理解するつもりですか?

20
Ruben

それはあなたがそれで何をしたいかによります。

住所が分かれていると、他の目的(USPSデータに対する検証やUPS/FEDEXからの配送料の取得など)に住所を使用する方が常に簡単であることがわかりました。

これは私がアドレスに通常使用するものです:

  • 住所1
  • 住所2
  • 住所3
  • 領域
  • 郵便番号

編集への応答:ほとんどの状況で、私はその用途を知りません。上記の表には、ほとんどの国の住所に対応できる十分なフィールドがあります(十分に汎用的です)。

8

住所

@BenAlabasterが提供した優れた答えの反対の極として、あなたは単に次のようにすることができます:

address       TEXT(300)
postal_code   VARCHAR(15)
country_code  VARCHAR(2)

クライアント側のフォームレイアウトは、必要に応じて複雑にすることもできます(または、ユーザーが手動で住所を入力できる複数行の入力を使用します)。その後、必要に応じてアドレスに改行を追加できます。

国テーブルは次のようになります。

country_code  VARCHAR(2)
country_name  VARCHAR(255)

さらに、次の1つを使用できます。

postal_code_required  TINYINT(1)
postal_code_regex     VARCHAR(255) NULL DEFAULT NULL

次に、次のリストを使用して国テーブルを設計します。

6
rybo111

この質問に遭遇した人のための逸話は次のとおりです。

私は多くの大陸(ヨーロッパ、アジア、北米)で生活し、働いてきた人物として話しています。私の経験と一緒に働く人々の経験では、次のようなシステムを使用する方がはるかに簡単になりました。

  1. 1つのアドレスを入力する3行を入力します。これらの3行を、私が入力したとおりに地域の郵便局に逐語的に渡します。必要な文字セットを使用させてください。 UTF-8またはより良いものを使用してください。
  2. 特定の情報(郵便番号、都道府県、都道府県など)を指定する必要があるビジネス要件がシステムにある場合は、別途それを要求してください。ビジネス要件とは、分析などのことです。これらの情報はお近くの郵便局と共有しないでください(上記のポイント1の3行のいずれかに同じ情報を書き込んだ場合を除きます)。
  3. 上記のポイント1の行に入力した住所のカテゴリ別の場所(国など)を指定するように求めるドロップダウンがあります。
  4. ポイント1の行で提供する情報を解析する必要がある場合は、ポイント3に対する私の答えを使用して正規表現を選択します。ポイント1の情報に対してその正規表現を実行して解析します。正規表現からの出力を使用して、ポイント2のユーザーインターフェイス要素を入力してみてください。自動入力された情報を修正した場合、正規表現を改善するために変更したという事実を利用してください。同様に、可能な限り、あなたの正規表現の出力を確認して修正する機会を私に与えてください。私が伝えようとしていたことを私よりも誰もよく知っていません。

このように構築されたシステムは、私の人生を最も簡単にします。特に、会社が実質的に機能的な内部知識を持たない郵便システムにメールを送信する場合は特にそうです。

あなたの会社が特定の郵便システムに関する内部知識を持っている場合は、ポイント3の私の選択を使用して、どのビューを表示するかを通知してください。多くの人々は、米国の郵便制度が包装に期待することを知っています。ポイント3で米国を選択した場合、ビューを米国の住所に適切に見えるようにしてください。あなたの会社が何も知らない国を選択した場合、一般的な3行を表示し、残りは私に任せます。 ASCIIの使用を強制しないでください。

そして、ここで本当のことをしましょう-すべてのグローバルな郵便システム(公的および私的)の完全な百科事典データベースを構築することは、不可能ではないにせよ、せいぜい非常に困難な作業です。たとえば、住所がどこにあるかをローカルのラストマイル運送業者だけが実際に知っている郵便システムがあります。時々、パッケージのそのキャリアにメモを渡すことができることは非常に便利です。そして、すべてのEdgeケースキャリアのローカルな知識をデータベースにマッピングすることは、実際には不可能な作業です。

ゲーデルにお尋ねください。 (そして、公理システムを使用して談話の宇宙をモデル化しようとしているのか、集合論や関係代数のようなある種の算術を与えているのか、または受けているのかを自問してください。)

3
StudentsTea

Ben Alabasterの回答のコメント:国に基づいて住所をフォーマットするには、国ごとの列の順序を個別の行として持つフォーマットテーブルを使用できます。

  • AddressFormat(CountryCode、FieldName、FieldOrder)

複雑なグリッドレイアウトを使用するようにフィールドの順序をコーディングすることもできます。

国ごとに住所を分けても意味がありません。国の数が増えるとこれは無秩序になり、たとえば国際的なクライアントのすべてのアドレスを検索したい場合、問題が発生します。ベンが提案した住所タイプを使用すると、建物番号とアパート番号の両方が含まれる住所がある場合に、あいまいさが生じる可能性があります。私は、各建物が異なる名前のアパートにいる可能性があります。これはインドでは非常に一般的です。

1
bkm

私は https://github.com/commerceguys/addressing ライブラリを使用して国際住所をフォーマットし、次の要素を使用します。

Country
Administrative area
Locality (City)
Dependent Locality (in: BR, CN, IR, MY, MX, NZ, PH, KR, ZA, TH)
Postal code
Sorting code
Address line 1
Address line 2
Organization
Recipient

通り(名前、家の番号など)を解析したい場合、これは役に立ちません。

ところで多言語の国リストを探している場合: https://github.com/umpirsky/country-list

1
Harald Ernst

唯一の方法は、それらを次のように分割することです。

Name varchar,
Title varchar,
StreetAddress varchar,
StreetAddressLine2 varchar,
zipCode varchar,
City varchar,
Province varchar,
Country lookup

なぜなら、ほとんどすべての国には、住所データを持つための独自の標準があり、国ごとに異なる形式の郵便番号があるからです。
同様の質問から my post に問題の小さなサンプルを含めることができます。

住所規則がほとんどない国があるため、すべての国で住所を分離しても意味がありません。いくつかの一般的な慣習には、小さな村に通りがないこと、村の名前と番号だけがあること、通りがより大きな都市の住所にあることが含まれます。ハンガリーの首都ブダペストでは、同じ名前の街路がいくつかあることを知っています(市の地区番号で区別します)が、他の都市にはそのような住所はありません(ハンガリーの誰かがこれが本当かどうか実際に確認する場合があります)。したがって、アドレス形式の総数は、numer_of_countriesにこの国のアドレス形式の数を掛けたものになります…さまざまなテーブルで実行できますが、それは大変な作業です。

0
smok1

これは既に回答済みの非常に古いトピックであることは知っていますが、2セントも投入すると思いました。それはすべて、プロジェクトの目的と、ターゲットユーザーがアドレスを入力することをどのように期待するかに依存します。ベンの提案により、住所を正確に解析できるようになりますが、その一方で、ユーザーデータの入力プロセスが長くなる可能性があります。 Stephen Wrightonの提案はより単純で、結果としてユーザーがアドレスを入力するのがより簡単になる可能性があります。

都市、国、地域などを維持しながら、典型的な通りの番号、タイプ、通りの名前、ユニット/アパートの番号などをすべて1つの列にキャプチャする「住所」列を含むモデルもいくつか見ました。他の列内。スティーブンのモデルに似ていますが、住所1、住所2、住所3がすべて1つの列に統合されています。

私の意見では、柔軟性の解釈に応じて、最も柔軟なモデルは最も制限の少ないモデルになる傾向があります。

0
Shan Plourde