GolangおよびPostgisを使用してアドレスバー(ストリート[ホーム])を解析する

こんにちは、%habrauser%。

先日、私は興味深い仕事に出会いました-ユーザーは、家のある通り、単なる通りであるか、まったくない通りである可能性のある線を入力します。

-それはもっと簡単に思えます-スペースで行を分けて楽しんでください-Stirlitzを考えた

「パベル・コルチャギン通りはどうですか」オブロミンゴ鳥がささやいた

「ええと、まあ、家番号はおそらく数字です」とスターリッツは言った。

-ええ、建物1-良い数

-ああ、あなたは車輪を再発明する必要があります





そしてShtiritsはGolangのプラスを明らかにし、Postgisをそれにロードしました...



そして、私たちが持っているのは、ランダムなユーザー入力デバイス 、特定の行、ユーザーが入力したものが家のある通りであるかどうかに応じて特定のアクションを実行する緊急の必要性です



const MARK_STEP = 20 func AnalyzeString(str string) (result int, street, house string) { result = 100 LastSpace := strings.LastIndex(str, " ") if LastSpace < 1 { result = 0 street = str return result, street, house } if LastSpace < (len([]rune(str)) - 6) { result -= MARK_STEP } else { result += MARK_STEP } street = str[:LastSpace] house = str[LastSpace+1:] if models.StreetCount(street) > 0 { result += MARK_STEP * 2 } else { result -= MARK_STEP * 2 } if models.StreetCount(str) > 0 { result -= MARK_STEP } else { result += MARK_STEP } if models.HouseCount(street, house) > 0 { result += MARK_STEP } else { result -= MARK_STEP * 4 } var int_count, char_count uint8 for _, run := range []rune(house) { if (run > 47) && (run < 58) { int_count++ } else { char_count++ } } switch { case char_count == 0: { result += MARK_STEP * 3 } case int_count == 0: { result -= MARK_STEP * 4 } case int_count == char_count: { result += MARK_STEP } case int_count > char_count: { result += MARK_STEP * 2 } case char_count > int_count: { result -= MARK_STEP } } return result, street, house }
      
      







それでは、この機能とは何ですか?

この関数は、ユーザーが入力した文字列を受け入れて分析し、家のある通り、別の通り、別の家である確率を返します。

確率が200を超える場合-安心できます-ユーザーは家のある通りを念頭に置いていました。



おそらく、StreetCount(通り)とHouseCount(通り、家)の呼び出しに気づいたでしょう

原則として、それらの背後には2つの平凡なSQLクエリがあります



 rows, err := DB.Query("SELECT COUNT(*) FROM planet_osm_line WHERE highway <> '' AND name ILIKE $1 ", "%"+name+"%")
      
      





そして

 rows, err := DB.Query("SELECT COUNT(house.*) FROM planet_osm_polygon AS house WHERE \"addr:street\" ILIKE $1 AND \"addr:housenumber\" ILIKE $2", "%"+streetName+"%", "%"+houseNum+"%")
      
      





それに応じて



そして、今、順番に

開始確率は100です。うまくいかない場合(スペースがない場合)、最後のスペースに従ってラインを分割します。それから、地獄には、これはすべて家のある通りではありません。

それが判明した場合、スペースの後に残っている文字数を調べます.6未満の場合(この数字は、他の多くの人がTyk Neb Finger教授の方法に従って選択される)、確率を増やす価値があり、それ以上である場合は、それを減らします。



何らかの形で確率を変更したり、ガベージコレクターに泣き叫ぶ機能を終了したりしても、叙事詩を続けます(まあ、または続けないで、ガベージおじさんは手放すのが好きではありません)。

最後のギャップの前のすべてが通りと見なされ、その後のすべてが家と見なされます。

次に、Postgisに、ユーザーが入力した通りの道路があるかどうかを確認し、ある場合は確率を上げ、そうでない場合は下げます(いいえ、外に出ません。その通りはまだデータベースにない可能性があります)。

次に、最初の行で道路のデータベースを検索しようとします。ある場合は、馬を保持して確率を下げる価値があります。そうでない場合は、ギャロップします。

同じ家の操作を繰り返し、同じ通りに同じ番号の家があるかどうかをPostgisに尋ねます。



さて、もう基地は必要ありません。

ここで、文字列を文字に分解し、持っている数字の数と、文字やその他の文字の数を計算します。対応するスイッチケースの構造を説明する必要はないと思います。



このようなcなマカーで、スターリッツは賭けの次のタスクを完了し、オブロミンゴの鳥を打ち負かし、王女からドラゴンを救い、マリオを置き換えました

みんなありがとう、誰もが無料で、私、Stirlitzは、Habrに行って読みます。



All Articles