作者CSDN:进击的西西弗斯
本文链接:https://blog.csdn.net/qq_42216093/article/details/120943532
版权声明:本文为作者原创文章,未经作者同意不得转载


1.项目说明以及流程概要

爬取网站:智联招聘(https://sou.zhaopin.com/)

开发环境:Python3.8(Pycharm编辑器),全流程通过代码实现

爬取时间:2021/10/24 晚上9:13 的实时招聘信息数据

爬取职位及城市:共9个职位,java开发、前端开发、算法、数据挖掘、数据开发、数据分析、硬件开发、运维、产品经理;由于本人在上海工作,因此本次爬取的城市限定为上海

主要用到的python库:requestsBeautifulSouppandasmatplotlibseaborn

项目说明:本人初入互联网行业工作,为了更深入地了解互联网行业各类职位的相关信息,我使用python在智联招聘网站爬取了9大热门职位的全部招聘信息数据,包括薪资、公司名称以及规模、学历要求、技能要求、工作经验要求等数据,对数据清洗和整理后进行可视化分析,得到了薪资分布、不同学历占比、技能词频图等结果,目的是能从繁杂的招聘数据中直观地看到有价值的信息。

2.爬取网站数据并整理为csv

流程概要:

根据url和相关参数获取网页的html,对html解析后正则提取我们需要的标签信息,最终以dataframe二维表形式保存为csv文件,**其中要注意:**智联招聘在未登陆状态下无法爬取职位数据,于是我们可以先登陆网站,然后在浏览器开发者模式下找到需求头信息(Request Headers),复制下来后通过copyheaders库转换为字典后加入requests请求的headers参数中。(建议不要直接使用我的代码,虽然可以运行但运行多了可能会被网站检测出爬虫并被反爬!)

代码:(附注释)

# version : python3.8
# -*- coding : utf-8 -*-
"""
Created on : 2021/10/24 5:13 下午
@Author  : liudong
@Software: PyCharm
"""import requests
import re
from copyheaders import headers_raw_to_dict
from bs4 import BeautifulSoup
import pandas as pd# 根据url和参数获取网页的HTML:def get_html(url, params):my_headers = b'''Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.9Accept-Encoding: gzip, deflate, brAccept-Language: zh-CN,zh;q=0.9Cache-Control: max-age=0Connection: keep-aliveCookie: x-zp-client-id=448f2b96-6b3a-48e3-e912-e6c8dd73e6cb; sts_deviceid=178832cf3f2680-0b20242883a4a9-6618207c-1296000-178832cf3f3780; Hm_lvt_38ba284938d5eddca645bb5e02a02006=1624877846; urlfrom2=121114584; adfcid2=www.google.com; adfbid2=0; FSSBBIl1UgzbN7NO=5QbLj2_L5kKhv8gnuJa.E1._8RKksG1y5Nt4FRrSajQ7PKGJ8CcWopqTuOLay__ida1esO2ud4AdXKKDI69j9UA; locationInfo_search={%22code%22:%22538%22%2C%22name%22:%22%E4%B8%8A%E6%B5%B7%22%2C%22message%22:%22%E5%8C%B9%E9%85%8D%E5%88%B0%E5%B8%82%E7%BA%A7%E7%BC%96%E7%A0%81%22}; selectCity_search=538; ssxmod_itna=7qGxnDRG0=KGqAKGHKiQRSDQwKfkKqYteb87Dla=xA5D8D6DQeGTb0NpYeYietdigMWPqKYG4iteiFlYfPtb+4OEdD84i7DKqibDCqD1D3qDkbCYxiinDCeDIDWeDiDG+8D0hXl7DjQNXZKkULfBNDz4X2/4UgQDDHfG024dLRIqIgFA+5HYbDbxp9DB6rxBQ/Iqj6znUDgMTTibwbj8DoGiP=fifwn7Dq0YoYCA44fDx=bb4ee2hso7DYFDqojR8DG4xL2iD===; ssxmod_itna2=7qGxnDRG0=KGqAKGHKiQRSDQwKfkKqYteb8D61Fgj40y4rP03aKenjt6D6QMTiBeG2Yn408DewGD; urlfrom=121114584; adfcid=www.google.com; adfbid=0; sts_sg=1; sts_chnlsid=Unknown; zp_src_url=https%3A%2F%2Fwww.google.com.hk%2F; LastCity=%E4%B8%8A%E6%B5%B7; LastCity%5Fid=538; sensorsdata2015jssdkcross=%7B%22distinct_id%22%3A%221071739258%22%2C%22first_id%22%3A%22178832cf3bd20f-0be4af1633ae3d-6618207c-1296000-178832cf3be4b8%22%2C%22props%22%3A%7B%22%24latest_traffic_source_type%22%3A%22%E8%87%AA%E7%84%B6%E6%90%9C%E7%B4%A2%E6%B5%81%E9%87%8F%22%2C%22%24latest_search_keyword%22%3A%22%E6%9C%AA%E5%8F%96%E5%88%B0%E5%80%BC%22%2C%22%24latest_referrer%22%3A%22https%3A%2F%2Fwww.google.com%2F%22%7D%2C%22%24device_id%22%3A%22178832cf3bd20f-0be4af1633ae3d-6618207c-1296000-178832cf3be4b8%22%7D; sts_sid=17cb28d33471536-08566241781bac-123b6650-1296000-17cb28d33481380; at=903f2985908c40b08a5f94a31f3ce3dc; rt=87ef0544ac924abaac9cfcddf07c9ea0; sts_evtseq=10; acw_tc=2760828b16350838102677392e6fd947253c8ceb8c6d07bf99f3246521c8ce; d4d6cd0b4a19fa72b8cc377185129bb7=843b9b24-97dd-410b-a554-cd40e82436ac; FSSBBIl1UgzbN7NP=53UYbECmTRPWqqqmZ7NMd1qzBpaBQmALgVHgfOadtkb30AZnPQLBe7tq5ITop.QpE0UAFelJGyiJUw4o9YrykPPl30M59JtVADHIlrqeL2qh7oUUJiEIrkb73XNoNod5EeRNheLNmf8wvi8F3yFwLBqPZ7.6CapWrCtXpfI4HapeY7.pC.nlnkSsRFcOC30dWn.1t5.wXdIYcgGeYZbRTyH2cYoRKwMJTnAAuuC6LHa9Ba4GAk0Ro6G8LN58ssLfFaIH8rfFDzN9_YTitsrxNXt; zpfe_probe_token=12c91e38s94ee345139aa73548b089ce0f18Host: sou.zhaopin.comReferer: https://www.zhaopin.com/sec-ch-ua: "Chromium";v="94", "Google Chrome";v="94", ";Not A Brand";v="99"sec-ch-ua-mobile: ?0sec-ch-ua-platform: "macOS"Sec-Fetch-Dest: documentSec-Fetch-Mode: navigateSec-Fetch-Site: same-originSec-Fetch-User: ?1Upgrade-Insecure-Requests: 1User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/94.0.4606.81 Safari/537.36    '''     # b:将字符串转换为二进制; 三引号:为输入多行字符串,即包含\n的字符串my_headers = headers_raw_to_dict(my_headers)  # 把复制的浏览器需求头转化为字典形式req = requests.get(url, headers=my_headers, params=params)req.encoding = req.apparent_encodinghtml = req.textreturn html# 输入url和城市编号,获取由所有职位信息的html标签的字符串组成的列表:def get_html_list(url, position):html_list = list()for i in range(1, 20):params = {'jl': '538', 'kw': position, 'p': str(i)}html = get_html(url, params)soup = BeautifulSoup(html, 'html.parser')html_list += soup.find_all(name='a', attrs={'class': 'joblist-box__iteminfo iteminfo'})     # 参数:名称,属性(化成字典)for i in range(len(html_list)):     # soup.find_all()得到的列表元素是特殊类型html_list[i] = str(html_list[i])return html_list# 根据上面的HTML标签列表,把每个职位信息的有效数据提取出来,保存csv文件:def get_csv(html_list):city, specific_position, company_name, company_size, company_type, salary, education, ability, experience = ([] for i in range(9))  # 多变量一次赋值for i in html_list:if re.search('<li class="iteminfo__line2__jobdesc__demand__item">(.*?)</li> <li class="iteminfo__line2__jobdesc__demand__item">(.*?)</li> <li class="iteminfo__line2__jobdesc__demand__item">(.*?)</li>',i):s = re.search('<li class="iteminfo__line2__jobdesc__demand__item">(.*?)</li> <li class="iteminfo__line2__jobdesc__demand__item">(.*?)</li> <li class="iteminfo__line2__jobdesc__demand__item">(.*?)</li>',i).group(1)city.append(s)s = re.search('<li class="iteminfo__line2__jobdesc__demand__item">(.*?)</li> <li class="iteminfo__line2__jobdesc__demand__item">(.*?)</li> <li class="iteminfo__line2__jobdesc__demand__item">(.*?)</li>',i).group(2)experience.append(s)s = re.search('<li class="iteminfo__line2__jobdesc__demand__item">(.*?)</li> <li class="iteminfo__line2__jobdesc__demand__item">(.*?)</li> <li class="iteminfo__line2__jobdesc__demand__item">(.*?)</li>',i).group(3)education.append(s)else:city.append(' ')experience.append(' ')education.append(' ')if re.search('<span class="iteminfo__line1__jobname__name" title="(.*?)">', i):s = re.search('<span class="iteminfo__line1__jobname__name" title="(.*?)">', i).group(1)specific_position.append(s)else:specific_position.append(' ')if re.search('<span class="iteminfo__line1__compname__name" title="(.*?)">', i):s = re.search('<span class="iteminfo__line1__compname__name" title="(.*?)">', i).group(1)company_name.append(s)else:company_name.append(' ')if re.search('<span class="iteminfo__line2__compdesc__item">(.*?) </span> <span class="iteminfo__line2__compdesc__item">(.*?) </span>',i):s = re.search('<span class="iteminfo__line2__compdesc__item">(.*?) </span> <span class="iteminfo__line2__compdesc__item">(.*?) </span>',i).group(1)company_type.append(s)s = re.search('<span class="iteminfo__line2__compdesc__item">(.*?) </span> <span class="iteminfo__line2__compdesc__item">(.*?) </span>',i).group(2)company_size.append(s)else:company_type.append(' ')company_size.append(' ')if re.search('<p class="iteminfo__line2__jobdesc__salary">([\s\S]*?)<', i):s = re.search('<p class="iteminfo__line2__jobdesc__salary">([\s\S]*?)<', i).group(1)s = s.strip()salary.append(s)else:salary.append(' ')s = str()l = re.findall('<div class="iteminfo__line3__welfare__item">.*?</div>', i)for i in l:s = s + re.search('<div class="iteminfo__line3__welfare__item">(.*?)</div>', i).group(1) + ' 'ability.append(s)table = list(zip(city, specific_position, company_name, company_size, company_type, salary, education, ability, experience))df = pd.DataFrame(table, columns=['city', 'specific_position', 'company_name', 'company_size', 'company_type', 'salary','education', 'ability', 'experience'])return dfif __name__ == '__main__':url = 'https://sou.zhaopin.com/'positions = ['java开发','前端开发','算法','数据挖掘','数据开发','数据分析','硬件开发','运维','产品经理']for i in positions:html_list = get_html_list(url, i)df0 = get_csv(html_list)position = [i]*(df0.shape[0])df_position = pd.DataFrame(position, columns=['position'])df = pd.concat([df_position, df0], axis=1)file_name = i + '.csv'df.to_csv(file_name)

结果:

结果文件csv下载链接

3.对数据结果进行可视化

流程概要:

先对数据结果进行清洗,salary属性下的字段都是类似于“8千-1.5万”这种无法进行后续统计和处理的字符串,我们需要将其全部修改为数值结果从而方便后续处理,此处我使用pandasre(正则表达式)把每个字段的薪资统一处理成了范围的中间值;对公司规模也采取类似处理,将描述性文字处理为数值型;最后将’薪资’和’公司规模’列的空值替换为各自列的均值。由于时间关系,还有其他空值、异常值等数据清洗并没有再继续处理。最后,使用matplotlibseaborn进行数据可视化,共得到4个结果图

代码:(附注释)

# version : python3.8
# -*- coding : utf-8 -*-
"""
Created on : 2021/10/24 3:42 下午
@Author  : liudong
@Software: PyCharm
"""import pandas as pd
import re
import numpy as np
import matplotlib.pyplot as plt
import seaborn as sns
from wordcloud import WordCloud
plt.rcParams['font.sans-serif'] = ['Heiti TC']    # 指定默认字体:解决plot不能显示中文问题
plt.rcParams['axes.unicode_minus'] = False           # 解决保存图像是负号'-'显示为方块的问题def data_clean():# 读取数据ls = ['java开发', '前端开发', '算法', '数据挖掘', '数据开发', '数据分析', '硬件开发', '运维', '产品经理']df = pd.read_csv('java开发.csv', index_col=0)for i in ls:if i != 'java开发':df0 = pd.read_csv(i + '.csv', index_col=0)df = pd.concat([df, df0], axis=0, ignore_index=True)# 清洗"薪资"列的数据,将文字描述处理成数值型for i in range(df.shape[0]):salary = df.loc[i, 'salary']if re.search(r'.*千-.*千', salary):a = eval(re.search('(.*)千-(.*)千', salary).group(1))*1000b = eval(re.search('(.*)千-(.*)千', salary).group(2))*1000num = (a+b)/2elif re.search(r'.*千-.*万', salary):a = eval(re.search('(.*)千-(.*)万', salary).group(1))*1000b = eval(re.search('(.*)千-(.*)万', salary).group(2))*10000num = (a+b)/2elif re.search(r'.*万-.*万', salary):a = eval(re.search('(.*)万-(.*)万', salary).group(1))*10000b = eval(re.search('(.*)万-(.*)万', salary).group(2))*10000num = (a+b)/2else:num = np.nandf.loc[i, 'salary'] = num# 清洗"公司规模"列的数据,将文字描述处理成数值型for i in range(df.shape[0]):s = df.loc[i, 'company_size']if re.search(r'(\d+)-(\d+)', s):a = eval(re.search(r'(\d+)-(\d+)', s).group(1))b = eval(re.search(r'(\d+)-(\d+)', s).group(2))n = round((a+b)/2,0)elif re.search(r'^(\d+)人', s):n = eval(re.search(r'^(\d+)人', s).group(1))else:n = np.nandf.loc[i, 'company_size'] = n# 将'薪资'和'公司规模'列的空值替换为各自列的均值df['salary'] = df['salary'].fillna(df['salary'].mean())df['company_size'] = df['company_size'].fillna(df['company_size'].mean())df.to_csv('df.csv')return dfdef visualization(df):# 图1:总体数据的薪资分布情况salarys = df['salary']/1000mean = round(salarys.mean(),1)plt.figure(figsize=(8,6),dpi=200)sns.distplot(salarys, hist = True, kde = True, kde_kws={"color":"r", "linewidth":1.5, 'linestyle':'-'})plt.axvline(mean, color='r', linestyle=":")plt.text(mean, 0.05, '平均月薪: %.1f千'%(mean), color='k', horizontalalignment = 'center', fontsize = 15)plt.xlim(0,60)plt.xlabel('月薪(单位:千)')plt.title('互联网行业的薪资分布')plt.savefig('./互联网行业的薪资分布.jpg')plt.show()# 图2:9大职位的平均薪资条形图salarys = []positions = list(set(list(df['position'])))     # 将职位列单独拉出来、去重、转化列表for i in positions:t = df.loc[df['position']==i, 'salary']salarys.append(round(t.mean()/1000, 1))data = pd.DataFrame(list(zip(positions, salarys)), columns = ['positions', 'salarys'])data = data.sort_values('salarys', ascending=False)fig = plt.figure(figsize=[8, 6], dpi=200)ax = fig.add_subplot()ax.bar(data['positions'], data['salarys'], alpha=0.8, color='dodgerblue')for i in zip(data['positions'], data['salarys'], data['salarys']):ax.text(i[0], i[1], i[2], horizontalalignment = 'center')ax.set_ylim(8, 30)ax.set_title('互联网热门职位的平均月薪(单位:千)')plt.savefig('./互联网热门职位的平均月薪.jpg')plt.show()# 图3:公司规模的分布data = df['company_size']plt.figure(figsize=(8,6),dpi=200)sns.distplot(data, rug=True, hist = False, kde = True, kde_kws={"color":"dodgerblue", "linewidth":2, 'linestyle':'-'})plt.xlim(0, 12000)plt.xlabel('公司规模(单位:人)')plt.title('互联网行业的公司规模分布')plt.savefig('./互联网行业的公司规模分布.jpg')plt.show()# 图4:学历要求情况的饼图data = pd.DataFrame(df['education'].value_counts())x = data.indexy = list(data.iloc[:, 0])fig = plt.figure(figsize=(8,6), dpi=200)ax = fig.add_subplot()explode = (0, 0, 0, 0, 0.2, 0.4, 0.6)ax.pie(y, labels=x, autopct='%.1f%%', explode=explode )ax.legend()ax.set_title('互联网行业对学历要求的占比')plt.savefig('./互联网行业对学历要求的占比.jpg')plt.show()# 图5:算法岗的技能要求词频图ability = df.loc[df['position']=='算法', 'ability']l = list(ability)for i in range(len(l)):l[i] = str(l[i])words = ''.join(l)cloud = WordCloud(font_path='/System/Library/Fonts/STHeiti Light.ttc',    # 设置字体文件获取路径,默认字体不支持中文background_color='white',    # 设置背景颜色  默认是blackmax_words=20,    # 词云显示的最大词语数量random_state = 3,  # 设置随机生成状态,即多少种配色方案collocations = False,    # 是否包括词语之间的搭配,默认True,可能会产生语意重复的词语width=1200, height=900      # 设置大小,默认图片比较小,模糊).generate(words)plt.figure(figsize=(8,6), dpi=200)plt.imshow(cloud)       # 该方法用来在figure对象上绘制传入图像数据参数的图像,cloud对象支持该函数plt.title('算法职位的技能要求关键词频统计')plt.axis('off')     # 设置词云图中无坐标轴plt.savefig("./算法职位的技能要求关键词频统计.jpg")plt.show()if __name__ == "__main__":df = data_clean()visualization(df)

结果:

1). 互联网热门职位总体数据的薪资分布情况:(直方图+核密度分布函数)

尽管不能代表全部,不过这9大热门职位的数千条数据足以作为参考。从图中可以看出,互联网行业的薪资分布大致符合左偏态分布,薪资分布的密集区间大约在12k-22k之间,而平均薪资18.5k在所有行业的招聘市场中处于偏高的位置,一些曾经热门的行业比如机械制造、土木工程、生物医药,如今和互联网相比都大势已去了。

2). 互联网9个热门职位的平均薪资条形图:(已降序处理)

可以看出,大部分职位之间的的薪资差距不是很大,然而算法岗可谓是一枝独秀,27.4k的平均月薪即便在普遍高薪的互联网行业内部也是鹤立鸡群的,究其主要原因,算法岗的能力要求、工作难度、工作强度都是这些职位里最高的,同时市场对这类人才的需求要大于供给,这些都是造成高薪的原因。

3). 互联网招聘中对学历要求的占比:

可以看出在互联网行业学历要求中,本科占比最大,为64.9%,其次是大专,而其余学历加起来只占不到10%,因此,互联网行业对于学历要求相对较低,反观如今国内研究生报考人数与日俱增,如果你不打算读研,那你可以尝试来互联网行业。

4). 算法岗技能要求关键词频统计:

由于时间关系,此处就以薪资最高的算法岗为例作词频图。从图中可以看出,算法岗主要需求技术是深度学习、Python、机器学习、C语言、图像识别等,因此熟练掌握这些技能能够增加求职中的核心竞争力。

有问题欢迎留言交流。
最后,如果你对Python、数据分析、机器学习等内容感兴趣,欢迎关注我的博客。

Python项目:爬取IT互联网高薪热门职位数据并进行可视化分析相关推荐

  1. 用Python爬取了2900多款防脱洗发水数据并进行可视化分析,助你缓解脱发困扰

    就在前段时间,一项由卫健委发起的脱发人群调查数据显示:中国受脱发问题困扰的人群高达2.5亿.听到这儿,远在韩国的各家媒体又开始出来搞事情了, 根据他们的计算,这些人完全脱发时的总脱发面积大约可达590 ...

  2. python项目-爬取妹子图

    最近在学爬虫,写了一个爬取妹子图片 功能:自动下载妹子图,并自动命名 网址:http://www.netbian.com/meinv/ #!/usr/bin/env python # -*- codi ...

  3. 每日一练:Python爬虫爬取全国新冠肺炎疫情数据实例详解,使用beautifulsoup4库实现

    Python 爬虫篇 - 爬取全国新冠肺炎疫情数据实例详解 效果图展示 第一章:疫情信息的下载与数据提取 ① 爬取页面数据到本地 ② json 字符串正则表达式分析 ③ 提取数据中的 json 字符串 ...

  4. python爬取微博数据词云_爬虫篇:使用Python动态爬取某大V微博,再用词云分析...

    这是我用大V冯大辉老师最近5000多条微博内容做的词云,大家可以围观一下. 之前也写了一篇用python 来爬取朋友的QQ说说,大家也可以围观一下 好了,开始进入正题:#coding:utf-8 &q ...

  5. python+requests+ 爬取官网双色球开奖数据

    python+requests+mysql 爬取官网双色球开奖数据 分析网页数据获取方式 第一种查询方式 第二种查询方式 完整代码 分析网页数据获取方式 第一种查询方式 在官网上 可以找到多种数据查询 ...

  6. 爬取BOSS直聘信息并进行清理和可视化分析(python小白)

    年底了,学习数据分析快四个月了.为了尽快找到一份数据分析相关的工作,计划把BOSS直聘上的相关职位都爬取下来分析分析,也好检验一下最近的学习成果.python新手,代码写的乱,将就看吧.首先,对给BO ...

  7. python爬虫——爬取拉勾上的职位信息

    爬取拉勾网站岗位数据 1.调用网页 查找网页链接规律 写一个for循环,爬取每一个网页的职位信息 def down():for i in range(1,4):if i == 1:strUrl = & ...

  8. 给大家整理了一篇Python+selenium爬取智联招聘的职位信息

    整个爬虫是基于selenium和Python来运行的,运行需要的包 1 mysql,matplotlib,selenium 需要安装selenium火狐浏览器驱动,百度的搜寻. 整个爬虫是模块化组织的 ...

  9. Python爬取‘跌妈不认’股票数据,绘制可视化图

    前言 本文的文字及图片来源于网络,仅供学习.交流使用,不具有任何商业用途,如有问题请及时联系我们以作处理. 以下文章来源于可以叫我才哥 ,作者才哥 大家好,上次我们试着用vba在excel中绘制树状热 ...

  10. 如何用Python自动爬取全国30+城市地铁图数据?

    阅读本文大概需要 3 分钟. 最近两天工作之余,开始涉猎python,自动爬取了全国30+城市地铁图数据,这里分享下整个爬虫过程 1. 数据来源 首先分析全国各个城市地铁图的数据来源,无非就是百度或者 ...

最新文章

  1. 少侠,找个千手观音来帮你营销可好?
  2. opencv 检测直线、线段、圆、矩形
  3. 用python+pillow模块实现抖音晃眼睛的特效,图像处理之路(附源码)
  4. Python 引用全局变量提示:local variable referenced before assignment. 问题解决办法,global使用方法介绍
  5. 如何利用云原生技术构建现代化应用
  6. 一些奇葩的元素节点object,video
  7. java写手机游戏_如何将自己编写的JAVA小游戏写到手机里?
  8. python flag 参数_flag_flagpython_js开关flag - 云+社区 - 腾讯云
  9. python 同步event对象
  10. 【第一部分】01Leetcode刷题
  11. HTML5--本地存储Web Storage
  12. CSS属性简写规则详解
  13. linux基础(一)——切换到root用户和普通用户
  14. Linux命令对应的英文全称
  15. 二级展开式斜齿圆柱齿轮减速器
  16. 计算机在运行表格的时候很慢,win7系统打开excel2007表格很慢的解决方法
  17. Redis数据类型和应用场景
  18. 一个屌丝程序员的青春(二五六)
  19. 动手学pytorch笔记整理12
  20. 国产ERP不如洋品牌但适合国能中小药企(转)

热门文章

  1. opencv mat与cvmat, iplimage转换
  2. 开源硬件USB抓包及协议分析工具分享
  3. centos下载和安装mongodb
  4. [译] Vue 最黑暗的一天
  5. sqlserver 企业版下载地址
  6. 计算机端口怎么配置波特率,怎么查看车载导航端口号、波特率和取码方式?
  7. 罗技鼠标的蓝牙适配器无效的解决办法
  8. MCJE魔改材质包教程
  9. 知乎 live 记录
  10. 机器视觉该怎么样系统学习