简体   繁体   English

缩短 MQTT 主题过滤 function

[英]Shorten MQTT topic filtering function

I wrote the following logic function, but I am sure it is possible to write it (way) shorter.我写了以下逻辑 function,但我确信可以将它(方式)写得更短。 In case you are unfamiliar with MQTT wildcards, you can read up on them here.如果您不熟悉 MQTT 通配符, 可以在此处阅读它们。

self is the topic we are "subscribed" to, containing zero or more wildcards. self是我们“订阅”的主题,包含零个或多个通配符。 incoming is the topic we received something on, which must match the self topic either fully, or conforming to the wildcard rules. incoming是我们收到的主题,它必须完全匹配self主题,或者符合通配符规则。

All my tests on this function succeed, but I just don't like the lengthiness and "iffyness" of this Scala function.我对这个 function 的所有测试都成功了,但我只是不喜欢这个 Scala function 的冗长和“不确定”。

def filterTopic(incoming: String, self: String): Boolean = {
  if (incoming == self || self == "#") {
    true
  } else if (self.startsWith("#") || (self.contains("#") && !self.endsWith("#")) || self.endsWith("+")) {
    false
  } else {
    var valid = true
    val selfSplit = self.split('/')
    var j = 0

    for (i <- selfSplit.indices) {
      if (selfSplit(i) != "+" && selfSplit(i) != "#" && selfSplit(i) != incoming.split('/')(i)) {
        valid = false
      }
      j += 1
    }

    if (j < selfSplit.length && selfSplit(j) == "#") {
      j += 1
    }

    j == selfSplit.length && valid
  }
}

Here's a shot at it assuming that '+' can be at the end and that the topics are otherwise well-structured这是一个镜头,假设“+”可以在最后并且主题在其他方面结构良好

    def filterTopic(incoming: String, self: String): Boolean = {
        // helper function that works on lists of parts of the topics
        def go(incParts: List[String], sParts: List[String]): Boolean = (incParts, sParts) match {
            // if they're the same list, the topics match
            case (is, ss) if is == ss => true
            // if sParts is just a single "#", the topics match
            case (_, "#" :: Nil) => true
            // if sParts starts with '+', just check if the rest match
            case (_ :: is, s :: ss) if s == "+" =>
                go(is, ss)
            // otherwise the first parts have to match, and we check the rest
            case (i :: is, s :: ss) if i == s =>
                go(is, ss)
            // otherwise they don't match
            case _ => false
        }

        // split the topic strings into parts 
        go(incoming.split('/').toList, self.split('/').toList)
    }

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM