MySQL查询匹配英国邮政编码,无论空格数量如何

Jon*_*ott 0 mysql sql geolocation postal-code

我有世界上最简单的表格,用于查找英国邮政编码的lat/lng值(加载完整的英国邮政编码数据):

CREATE TABLE postcodes (
  postcode char(7) NOT NULL,
  lat double(10,6) NOT NULL,
  lng double(10,6) NOT NULL,
  KEY postcode (postcode)
)
Run Code Online (Sandbox Code Playgroud)

"邮政编码"字段中的邮政编码在前半部分的末尾有2位数字,或者一个空格.我认为这个空间对于它们如何匹配(??)的完整性很重要,而且我不想删除表中的空格,因为我还要拔出用于显示目的的邮政编码(我不喜欢我想要一个重复的领域,因为我很挑剔!).例子:

'LE115AF', 'BS6 5EE', 'W1A 1AA', 'BS216RS', 'M3 1NH'
Run Code Online (Sandbox Code Playgroud)

所以,有些有空格,有些则没有空格.大多数是7个字符,有些只有6个字符.

无论如何,重点是我希望用户能够输入邮政编码查询,包括部分邮政编码,有或没有空格,并且如果他们的输入字符串有效,总是找到匹配(即他们不输入完整或部分邮政编码,表中没有.

这是我到目前为止所做的事情(在PHP的帮助下):

{...} WHERE `postcode` LIKE '" . str_replace(' ','%',$query) . "%' LIMIT 1
Run Code Online (Sandbox Code Playgroud)

这适用于:

  • db中没有空格的完整邮政编码
  • 部分邮政编码,如果已经输入空格并且数据库中有相应的空格,或者查询部分没有空格发生的位置(例如'W1A'将匹配'W1A 1AA','M3 1'将匹配'M3 1AR '等等).

但不适用于这些查询:

  • 'W1A1AA'应匹配'W1A 1AA'
  • 'BS65EE'应匹配'BS6 5EE'
  • 'BS65'应匹配db中的第一个'BS6 5%'邮政编码,即"BS6 5AA"
  • 'M31'应该同样匹配'M3 1AR'

我猜我需要以某种方式做一些MySQL字符串函数魔法,如果行的邮政编码字段中有空格,并相应地调整我的WHERE子句逻辑?有人对最佳方法有任何建议吗?我理想的还想:

  • 避免MySQL存储过程(首选内联函数)
  • 除了PHP部分中的内联字符串函数之外,什么都不做

Mat*_*son 5

创建一个新列,它只是剥离了空格的邮政编码字段,并在其上创建一个唯一索引.你不应该找到任何重复.这应该让你放心,这个空间真的不重要:)

在剥离输入邮政编码上的空格后,将用于查找.

请记住,涉及将字符串函数应用于postcode表的列的解决方案可能会阻止MySQL使用该列上的任何索引.(索引基于列中的确切数据,因此,如果您开始将函数应用于该数据,则优化器通常会确定该索引是无用的.)

如果你觉得有必要重新格式化,那么最简单的选择就是知道,虽然邮政编码的"出站"部分 - 空格之前的部分 - 格式有点不同,"入站"部分 - - 空格的部分- 始终是一个数字,后跟两个字母.

顺便提一下,我发现的格式上最好的资源就是维基百科条目.