scala 查询ip归属地 测试

package com.ws.spark
import scala.io.Source
import scala.reflect.io.Path

/**
  * 查找ip归属地
  */
object IpFromUtils {

  def main(args: Array[String]): Unit = {
    val ip = ipToLong("211.97.160.75")
    val tuples: Array[(Long, Long, String)] = rules("E:\\bigData\\testdata\\ip.txt")

    val result: Int = binarySearch(tuples, ip)

    if (result == -1)
      return

    val ipForm: (Long, Long, String) = tuples(result)

    println(ipForm)
  }

  /**
    * ip转换10进制
    *
    * @param ip
    * @return
    */
  def ipToLong(ip: String): Long = {

    val ipArr = ip.split("[.]")

    var ipNum = 0L;

    for (i <- ipArr) {
    // | : 按位或运算 ,位运算符,相同位数主要出现1都为1,如(1|1=1,1|0=1,0|1=1)
    // ^ : 异或运算符,2数相同为0,不同为1,如(0^0=0,1^1=0)
      ipNum = i.toLong | ipNum << 8
    }

    ipNum
  }

  /**
    * 生成规则
    *
    * @param filePath
    * @return
    */
  def rules(filePath: String): Array[(Long, Long, String)] = {
    val path = Source.fromFile(filePath.toString())

    val array: Array[(Long, Long, String)] = path.getLines().map(lines => {
      val strArr = lines.split("[|]")
      val ipNum1 = strArr(2).toLong
      val ipNum2 = strArr(3).toLong
      val provnice = strArr(6)
      (ipNum1, ipNum2, provnice)
    }).toArray

    array
  }

  def generalRules(line : String): (Long, Long, String)={
    val strArr = line.split("[|]")
    val ipStart = strArr(2).toLong
    val ipEnd = strArr(3).toLong
    val province = strArr(6)
    (ipStart, ipEnd, province)
  }

  /**
    * 二分法(前提有序)
    */
  def binarySearch(array: Array[(Long, Long, String)], num: Long): Int = {
    var end = array.length - 1;
    var begin = 0;

    while (begin <= end) {
      val middle = (begin + end) >> 1;


      if (num >= array(middle)._1 && num <= array(middle)._2) {
        return middle
      }

      if (num < array(middle)._1) {
        end = middle - 1
      }
      else {
        begin = middle + 1
      }

    }

    -1
  }
}

猜你喜欢

转载自blog.csdn.net/bb23417274/article/details/82934587