我试图给出一个正则表达式来匹配某个基本路径。规则应该是匹配基本路径本身加上“ /”或“。”。和路径的其余部分。
例如,给定/ api / ping,以下内容应匹配
/api/ping.json
/api/ping
/api/ping/xxx/sss.json
/api/ping.xml
这应该不匹配
/api/pingpong
/api/ping_pong
/api/ping-pong
我尝试了以下正则表达式:
/api/ping[[\.|\/].*]?
但是似乎没有抓住/api/ping
的情况
这是link的正则表达式风暴测试仪
-
更新:多亏了答案,现在我有了这个版本,可以更好地反映我的推理:
\/api\/ping(?:$|[.\/?]\S*)
表达式在ping后(即$
部分结束),或者以.
,/
或?
继续,后跟任意非空格字符
这是regex
答案 0 :(得分:4)
您可以使用此正则表达式使用正则表达式来确保基本路径后跟 class CircleScoreView: UIView {
private let outerCircleLayer = CAShapeLayer()
private let outerCircleGradientLayer = CAGradientLayer()
private let outerCircleLineWidth: CGFloat = 5
override init(frame: CGRect) {
super.init(frame: .zero)
}
required init?(coder aDecoder: NSCoder) {
fatalError("init(coder:) has not been implemented")
}
override func layoutSubviews() {
super.layoutSubviews()
buildLayers()
}
/// Value must be within 0...100 range
func setScore(_ value: Int, animated: Bool = false) {
if value != 0 {
let clampedValue: CGFloat = CGFloat(value.clamped(to: 0...100)) / 100
if !animated {
outerCircleLayer.strokeEnd = clampedValue
} else {
let outerCircleAnimation = CABasicAnimation(keyPath: "strokeEnd")
outerCircleAnimation.duration = 1.0
outerCircleAnimation.fromValue = 0
outerCircleAnimation.toValue = clampedValue
outerCircleAnimation.timingFunction = CAMediaTimingFunction(name: .easeInEaseOut)
outerCircleLayer.strokeEnd = clampedValue
outerCircleLayer.add(outerCircleAnimation, forKey: "outerCircleAnimation")
}
outerCircleGradientLayer.colors = [Constant.Palette.CircleScoreView.startValue.cgColor,
Constant.Palette.CircleScoreView.middleValue.cgColor,
Constant.Palette.CircleScoreView.endValue.cgColor]
}
}
private func buildLayers() {
// Outer background circle
let arcCenter = CGPoint(x: frame.size.width / 2, y: frame.size.height / 2)
let startAngle = CGFloat(-0.5 * Double.pi)
let endAngle = CGFloat(1.5 * Double.pi)
let circlePath = UIBezierPath(arcCenter: arcCenter,
radius: (frame.size.width - outerCircleLineWidth) / 2,
startAngle: startAngle,
endAngle: endAngle,
clockwise: true)
// Outer circle
setupOuterCircle(outerCirclePath: circlePath)
}
private func setupOuterCircle(outerCirclePath: UIBezierPath) {
outerCircleLayer.path = outerCirclePath.cgPath
outerCircleLayer.fillColor = UIColor.clear.cgColor
outerCircleLayer.strokeColor = UIColor.black.cgColor
outerCircleLayer.lineWidth = outerCircleLineWidth
outerCircleLayer.lineCap = CAShapeLayerLineCap.round
outerCircleGradientLayer.startPoint = CGPoint(x: 0.0, y: 0.5)
outerCircleGradientLayer.endPoint = CGPoint(x: 1.0, y: 0.5)
outerCircleGradientLayer.frame = bounds
outerCircleGradientLayer.mask = outerCircleLayer
layer.addSublayer(outerCircleGradientLayer)
}
}
或.
或行/
的结尾
$
说明:
\/api\/ping(?=\.|\/|$)\S*
-逐字匹配\/api\/ping
文本/api/ping
-前瞻性确保其后是文字点(?=\.|\/|$)
或斜杠.
或行/
的结尾$
-可以选择在路径后跟随任何非空格字符在正则表达式中,\S*
字符集/api/ping[[\.|\/].*]?
的使用是不正确的,在这种情况下,您不需要转义点[]
,而不必替换.
字符集中需要的字符,并且不能通过将|
放在字符类中来完成,而且由于字符类看起来是嵌套的,因此这不是必需的,也不是正确的事情。我猜你想让正则表达式变成这样,
|
Demo with your corrected regex
注意,一旦在\/api\/ping([.\/].*)?$
中放置任何内容,它就仅被视为一个字符,从而允许字符集中包含所有内容,因此它允许点[]
或斜杠.
并注意您需要以/
的身份逃脱/
答案 1 :(得分:1)
您的模式使用character class,它将与列出的任何内容匹配,也可以写为[[./|]
。
它与/api/ping
不匹配,因为字符类必须至少匹配1次,因为它不是可选的。
您可以使用alternation来匹配/api/ping
,然后声明字符串的末尾,或者|
来匹配结构,方法是重复0次或更多次匹配正斜杠,而不是正斜杠,后跟一个点和1+次,然后是一个点和扩展名。
/api/ping(?:(?:/[^/\s]+)*\.\S+|$)
这将匹配
/api/ping
字面上匹配(?:
非捕获组
(?:/[^/\s]+)*
将匹配/
的分组结构重复0+次,然后再重复/
或空白字符1次以上的分组结构\.\S+
匹配一个点和一个非空格字符1倍以上|
或$
声明字符串的结尾)
关闭非捕获组请参见regex demo | C# demo