Go面试编程题目(五)

161 篇文章 12 订阅

原文地址:Go面试编程题目(五)

1、词频统计?

从文件中读取一篇文章,统计词频,按单词出现的频率从大到小进行排序,后写入到文件,实现代码如下:

package main

import (
  "encoding/json"
  "fmt"
  "io/ioutil"
  "log"
  "os"
  "sort"
  "strings"
  "unicode"
)

func getWordFrequency(readFilePath string, writeFilePath string) {
  var fileText string
  var wordFrequencyMap = make(map[string]int)
  //读取文件
  fileData, err := ioutil.ReadFile(readFilePath)
  if err != nil {
    log.Fatal(err)
  }

  fileText = string(fileData)
  //去掉分隔符
  f := func(c rune) bool {
    if !unicode.IsLetter(c) && !unicode.IsNumber(c) {
      return true
    }
    return false
  }

  arr := strings.FieldsFunc(fileText, f)
  //如果字典里有该单词则加1,否则添加入字典赋值为1
  for _, v := range arr {
    if _, ok := wordFrequencyMap[v]; ok {
      wordFrequencyMap[v] = wordFrequencyMap[v] + 1
    } else {
      wordFrequencyMap[v] = 1
    }
  }

  //按照单词出现的频率排序
  type wordFrequencyNum struct {
    Word string
    Num  int
  }

  var lstWordFrequencyNum []wordFrequencyNum
  for k, v := range wordFrequencyMap {
    lstWordFrequencyNum = append(lstWordFrequencyNum, wordFrequencyNum{k, v})
  }

  sort.Slice(lstWordFrequencyNum, func(i, j int) bool {
    return lstWordFrequencyNum[i].Num > lstWordFrequencyNum[j].Num
  })

  fmt.Println("按照单词出现频率由高到低排序", lstWordFrequencyNum)

  //写入文件
  var jsonBytes []byte
  var arrJsonBytes string
  for _, v := range lstWordFrequencyNum {
    jsonBytes, err = json.Marshal(v)
    if err != nil {
      log.Fatal(err)
    }
    arrJsonBytes = arrJsonBytes + string(jsonBytes)
  }

  err = ioutil.WriteFile(writeFilePath, []byte(arrJsonBytes), os.ModePerm)
  if err != nil {
    log.Fatal(err)
  }

}

func main() {
  readFilePath := "D:\\tools\\workSpace\\algorithm-算法\\Leecode\\read.txt"   //读取的文件路径
  writeFilePath := "D:\\tools\\workSpace\\algorithm-算法\\Leecode\\write.txt" //写入的文件路径
  getWordFrequency(readFilePath, writeFilePath)
}

写入文件部分也可替换成如下代码:
 

  //写入文件
  var arrJsonBytes string
  arrJsonBytes = arrJsonBytes + "[" + "\r\n"
  for k, v := range lstWordFrequencyNum {

    arrJsonBytes = arrJsonBytes + "{" + "\"" + v.Word + "\"" + ":" + strconv.Itoa(v.Num) + "}"
    if k != len(lstWordFrequencyNum)-1 {
      arrJsonBytes = arrJsonBytes + "," + "\r\n"
    }
  }
  
  arrJsonBytes = arrJsonBytes + "\r\n" + "]"
  err = ioutil.WriteFile(writeFilePath, []byte(arrJsonBytes), os.ModePerm)
  if err != nil {
    log.Fatal(err)
  }

2、在无序不重复数组中找出两个元素相加值为100的有多少对?

最简单直观的方法就是穷举法,也就是从数组中任意找两个数,看其和是否为给定值,时间复杂度为O(N^2)。

这里考虑使用hash表法,先定义一个map,开始为空,不存数据,之后遍历数组,判断第一个元素是否有另一半已经在map中,如果有count++,反之将第一个元素存入map,继续遍历第二个元素,判断第二个元素是否有另一半已经在map中,如果有count++,没有的话,把第二个元素存入map,重复操作至遍历结束,结果也出来了,实现代码如下:

package main

import "fmt"

func getSumNum(arr []int, sum int) int {
  tp := make(map[int]int)            //map存数组里的元素,注意,这里map初始为空
  var count int                      //计个数
  for i := 0; i <= len(arr)-1; i++ { //遍历数组
    //判断这个元素的“另一半”是否已经在map里
    if _, ok := tp[sum-arr[i]]; ok { //如果在,就说明数组中有这个元素的“另一半”
      count++
    } else { //如果不在,就把这个元素加入map中
      tp[arr[i]] = i
    }
  }

  return count
}

func main() {
  var brr []int = []int{1, 12, 14, 40, 56, 60, 88, 78, 99}
  var sum int = 100
  fmt.Println(getSumNum(brr, sum))
}

打印结果如下:

至此,本次分享就结束了,后期会慢慢补充。

以上仅为个人观点,不一定准确,能帮到各位那是最好的。

好啦,到这里本文就结束了,喜欢的话就来个三连击吧。

扫码关注公众号,获取更多优质内容。

  

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

luyaran

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值