Regex выпуска python захват группы, которая может существовать, но не всегда существует - PullRequest
1 голос
/ 02 апреля 2020

Я пытался в течение 1 часа, чтобы выяснить это на regex101 ... но я не решил это. Вот небольшой список, который проходит через мое регулярное выражение:

list = ["This.is.Test.Nr.One.C01B01.42U.Rack.08-Datacenter1",
        "Is.this.Nr.Two.C03B03.London.48U.Rack.04-Datacenter4",
        "This.Number.Random.C02.Frankfurt.42U.Rack.12-Datacenter1",
        "This.is.Random.Number.C08B01.Zuerich.Rack.01-Datacenter2"

Теперь я хочу захватить 5 групп. Я попробовал следующее регулярное выражение: \A(.+)\.(C\d{1,2})(B\d{1,2})?.?(42U|48U)?.+-(.+)

Group1:

This.is.Test.Nr.One
Is.this.Nr.Two
This.Number.Random
This.is.Random.Number

Group2:

C01
C03
C02
C08

Group3:

B01
B03
**missing but should still work for all the other groups**
B01

Group4:

42U
48U
42U
**missing but should still work for all the other groups**

Группа 5:

Datacenter1
Datacenter4
Datacenter1
Datacenter2

РЕДАКТИРОВАТЬ: Я думаю, что может быть и такой случай:

Is.this.Nr.Two.B03.London.48U.Rack.04-Datacenter4

Ответы [ 3 ]

2 голосов
/ 02 апреля 2020

Одним из способов является сопоставление с частями C, B и U и использование групп захвата внутри

^(?:(.+?)\.(C\d{1,2}))?(?:.*?(B\d{1,2}))?\.(?:.*?(42U|48U))?.*-(.+)$

Regex demo

0 голосов
/ 02 апреля 2020
(.+)\.(C\d{1,2})?(B\d{1,2})?(?:\.[A-Za-z]+)*\.(42U|48U)?.+-(.+)

будет работать.
Код тестирования следующий:

import re

list_ = [
    "This.is.Test.Nr.One.C01B01.42U.Rack.08-Datacenter1",
    "Is.this.Nr.Two.C03B03.London.48U.Rack.04-Datacenter4",
    "This.Number.Random.C02.Frankfurt.42U.Rack.12-Datacenter1",
    "This.is.Random.Number.C08B01.Zuerich.Rack.01-Datacenter2",
    "Is.this.Nr.Two.B03.London.48U.Rack.04-Datacenter4",
]


pattern = re.compile(
    r'(.+)\.'  # group1 and trailing literal "."
    r'(C\d{1,2})?'  # group2(optional)
    r'(B\d{1,2})?'  # group3(optional)
    r'(?:\.[A-Za-z]+)*\.'   # skipping for example multiple ".London" and "."
    r'(42U|48U)?.+-'  # group4(optional) and ... -
    r'(.+)'  # group5
)
for text in list_:
    match_object = pattern.search(text)
    if match_object:
        print(match_object.groups())
    else:
        print('Not matched')

вывод:

('This.is.Test.Nr.One', 'C01', 'B01', '42U', 'Datacenter1')
('Is.this.Nr.Two', 'C03', 'B03', '48U', 'Datacenter4')
('This.Number.Random', 'C02', None, '42U', 'Datacenter1')
('This.is.Random.Number', 'C08', 'B01', None, 'Datacenter2')
('Is.this.Nr.Two', None, 'B03', '48U', 'Datacenter4')
0 голосов
/ 02 апреля 2020

Последний был сумасшедшим, но это то, что работает.

^([a-zA-Z.]*\.)(C\d{1,2})?(B\d{1,2})?([.A-Za-z]*)(42U|48U)?.+-(.+)

Ссылка

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...