2016-10-31 2 views
0

Я не знаком с обозначениями «Мне нравится», # и * используется там, где они были, я хотел бы немного проверить здесь. Этот фрагмент кода в Интернете и хотел бы знать, делает ли он это как следует. Код, плюс некоторые некоторые комментарии я включил:Почтовый индекс Валидация и как обозначение

Function ValidPostCode(ByVal PostCode As String) As Boolean 
    '---------------------------------------------------------- 
    ' Deals with the postcodes of the form: 
    'AN NAA 
    'ANN NAA 
    'AAN NAA 
    'ANA NAA 
    'AANA NAA 
    'AANN NAA 
    'has issues with spaces and obscure entries like "England". 
    'Notes from Wiki:: 
'As all formats end with 9AA, the first part of a postcode can easily be extracted by ignoring the last three characters 
'Areas with only single-digit districts: BR, FY, HA, HD, HG, HR, HS, HX,  JE, LD, SM, SR, WC, WN, ZE (although WC is always subdivided by a further letter, e.g. WC1A). 
'Areas with only double-digit districts: AB, LL, SO. 
'Areas with a district '0' (zero): BL, BS, CM, CR, FY, HA, PR, SL, SS (BS is the only area to have both a district 0 and a district 10). 
'The following central London single-digit districts have been further divided by inserting a letter after the digit and before the space: EC1–EC4 (but not EC50), SW1, W1, WC1, WC2, and part of E1 (E1W), N1 (N1C and N1P), NW1 (NW1W) and SE1 (SE1P). 
    'The letters QVX are not used in the first position. 
'The letters IJZ are not used in the second position. 
    'The only letters to appear in the third position are ABCDEFGHJKPSTUW when the structure starts with A9A. 
    'The only letters to appear in the fourth position are ABEHMNPRVWXY when the structure starts with AA9A. 
    'The final two letters do not use the letters CIKMOV, so as not to resemble digits or each other when hand-written. 
'Post code sectors are one of ten digits: 0 to 9 with 0 only used once 9 has been used in a post town, save for Croydon and Newport (see above). 

'----------------------------------------------------------- 
Dim Parts() As String 
    PostCode = UCase$(PostCode) 
Parts = Split(PostCode) 
If PostCode = "GIR 0AA" Or PostCode = "SAN TA1" Or _ 
    (Parts(1) Like "#[A-Z][A-Z]" And _ 
    (Parts(0) Like "[A-Z]#" Or Parts(0) Like "[A-Z]#[0-9ABCDEFGHJKSTUW]" Or _ 
    Parts(0) Like "[A-Z][A-Z]#" Or Parts(0) Like "[A-Z][A-Z]#[0-9ABEHMNPRVWXY]")) Then 
    ValidPostCode = ((Parts(0) Like "[BEGLMSW]#*" Or _ 
         Parts(0) Like "A[BL]#*" Or _ 
         Parts(0) Like "B[ABDHLNRST]#*" Or _ 
         Parts(0) Like "C[ABFHMORTVW]#*" Or _ 
         Parts(0) Like "D[ADEGHLNTY]#*" Or _ 
         Parts(0) Like "E[CHNX]#[AMNRVY]" Or _ 
         Parts(0) Like "F[KY]#*" Or _ 
         Parts(0) Like "G[LU]#*" Or _ 
         Parts(0) Like "H[ADGPRSUX]#*" Or _ 
         Parts(0) Like "I[GPV]#*" Or _ 
         Parts(0) Like "K[ATWY]#*" Or _ 
         Parts(0) Like "L[ADELNSU]#*" Or _ 
         Parts(0) Like "M[EKL]#*" Or _ 
         Parts(0) Like "N[EGNPRW]#*" Or _ 
         Parts(0) Like "O[LX]#*" Or _ 
         Parts(0) Like "P[AEHLOR]#*" Or _ 
         Parts(0) Like "R[GHM]#*" Or _ 
         Parts(0) Like "S[AEGKLMNOPRSTWY]#*" Or _ 
         Parts(0) Like "T[ADFNQRSW]#*" Or _ 
         Parts(0) Like "W[ACDFNRSV]#*" Or _ 
         Parts(0) Like "UB#*" Or _ 
         Parts(0) Like "YO#*" Or _ 
         Parts(0) Like "ZE#*") And _ 
         Parts(1) Like "*#[!CIKMOV][!CIKMOV]") 
Else 
    ValidPostCode = False 
End If 
End Function 

Пожалуйста, если кто-то может помочь и, возможно, объяснить код тщательно я был бы очень благодарен.

Спасибо

+1

Использование регулярных выражений может быть проще. –

+1

Вот ссылка документации Microsoft: [VBA Like Operator] (https://msdn.microsoft.com/en-us/library/office/gg251796.aspx). Документы VBA являются золотым рудником информации и стоят закладок. –

ответ

1

Что-то вроде этого, используя VB Script Регулярные выражения

Function VALIDATE_PCODE(strPostCode As String) As Boolean 

Dim R As RegExp 

Set R = New RegExp 

' Validate AB## and AC# post codes 

With R 
    .MultiLine = False 
    .IgnoreCase = True 
    .Global = True 
    .Pattern = "^AB\d{1,2} |AC\d{1} " ' can use [0-9] here as \d 
End With 

VALIDATE_PCODE = R.Test(strPostCode) 

Set R = Nothing 

End Function 

EDIT

Используя то, что вы поставляется, вы могли бы построить что-то вроде рисунка ниже.

Function Validate_PostCode(strPostCode As String) As Boolean 

Const cstSingleDigit As String = _ 
    "BR,FY,HA,HD,HG,HR,HS,HX,JE,LD,SM,SR,WC,WN,ZE" 
Const cstDoubleDigit As String = _ 
    "AB,LL,SO" 

Dim arrTemp() As String 
Dim strRegExPattern As String 
Dim intCounter As Integer 
Dim rgeRegExp As RegExp 

' Build the Reg Ex pattern 

strRegExPattern = "^" 

arrTemp = Split(cstSingleDigit, ",") 

For intCounter = 0 To UBound(arrTemp) 

    strRegExPattern = strRegExPattern & _ 
         IIf(intCounter > 0, "|", "") & _ 
         arrTemp(intCounter) & "\d{1} " 

Next intCounter 

Erase arrTemp 

arrTemp = Split(cstDoubleDigit, ",") 

For intCounter = 0 To UBound(arrTemp) 

    strRegExPattern = strRegExPattern & "|" & _ 
         arrTemp(intCounter) & "\d{2} " 

Next intCounter 

Set rgeRegExp = New RegExp 

rgeRegExp.Global = True 
rgeRegExp.IgnoreCase = True 
rgeRegExp.Pattern = strRegExPattern 

Validate_PostCode = rgeRegExp.Test(strPostCode) 

End Function 
+0

Я предполагаю, что это для Великобритании - [этот ответ] (http://stackoverflow.com/a/164994/4088852) дает официально поставленное регулярное выражение. – Comintern

+0

Отличные парни, спасибо. У нас есть обновленный RegEx, поставляемый правительством? Мы знаем об одном ...? Кто угодно? Мы знаем, где его взять? –

1

Я обычно использую это Reg Ex для проверки почтовых индексов (рисунок всегда можно улучшить, но это не подводил меня еще) - будет возвращать почтовый индекс или ошибка #value.

'Returns the postcode or #VALUE error when used as worksheet function. 
'Use the 'OR alternatives if being called from within VBA - will return TRUE/FALSE on matches. 
Public Function ValidatePostCode(strData As String) As String 'OR Boolean 
    Dim RE As Object, REMatches As Object 

    Set RE = CreateObject("vbscript.regexp") 
    With RE 
     .MultiLine = False 
     .Global = False 
     .IgnoreCase = True 
     .Pattern = "^([A-PR-UWYZ0-9][A-HK-Y0-9][AEHMNPRTVXY0-9]?[ABEHMNPRVWXY0-9]? {1,2}[0-9][ABD-HJLN-UW-Z]{2}|GIR 0AA)$" 
    End With 

    Set REMatches = RE.Execute(strData) 

    ValidatePostCode = REMatches(0) 'OR REMatches.Count > 0 

End Function 
+0

Извините Даррена, последняя строка, похоже, возвращает ошибку времени выполнения - неверная процедура или аргумент? Что кажется очень странным? –

+1

Это странно - отлично работает на моем ... на самом деле, просто проверено, как обычно я использую его как функцию рабочего листа. Кажется, если он вызван из VBA, он выдает ошибку на недопустимые почтовые индексы: '? ValidatePostCode (" AB1 0AAz ")'. Это связано с тем, что 'REMatches' возвращает число 0 без соответствия, поэтому вы не можете смотреть на первое совпадение на этом - измените эту последнюю строку на' ValidatePostCode = REMatches.Count> 0' и возвращаемый тип функции на 'Boolean' - вы получите TRUE/FALSE ответы. Я обновил свой код с помощью альтернативы VBA. –

+0

Существует несколько почтовых индексов, которые не соответствуют этому шаблону (правильные почтовые индексы, но выше сказано иначе), которые я нашел: W1D 4RW, W1D 4SG, W1D 4SN, W1D 5DF, W1D 5EQ W1D 5ND ... как бы отрегулировать шаблон, чтобы исправить это. –

 Смежные вопросы

  • Нет связанных вопросов^_^