Python课程设计大作业:获取比赛数据并进行机器学习智能预测NBA的比赛结果

2023-05-16

前言

该篇是之前遗漏的大三上的Python课程设计。刚好今天有空就补发了一篇文章。全部的代码在最后附录中。爬虫类的代码直接全部放到一起了,读者可以自行研究。百度网盘可以私聊我进行获取。
在这里插入图片描述

一、课程设计项目说明

该课程设计项目亮点:

1、使用Python获取NBA每一年的比赛季后赛常规赛等部分项目中需要的比赛统计数据并输出成csv格式的文件。

二、课程设计项目功能

首先可通过Python获取的任意年度的球队数据,保存在本地文件夹后,更改名为“nwz”的代码中的路径folder为数据文件路径,即可导入球队各类数据而后进行特征向量、逻辑回归、球队的EloScore计算等机器学习,最终将预测的比赛结果输出到特定路径下的格式为.csv的文件查看比赛预测结果。

三、项目所需数据文件

本项目中一共需要5张数据表,分别是Team Per Ganme Stats(各球队每场比赛数据统计)、Opponent Per Game Stats(对手平均平常比赛的数据统计)、Miscellaneous Stats(各球队综合统计数据表)、2015-2016 NBA Schedule and Results(2015-16赛季比赛安排与结果)、2016-2017 NBA Schedule and Results(2016-2015赛季比赛安排)。

四、项目原理介绍

1、比赛数据介绍

本项目中,采用来自某网站的数据。可以获取到任意球队、任意球员的各类比赛统计数据,如得分、投篮次数、犯规次数等等。

我们主要使用2015-16赛季中的数据,分别是:
Team Per Ganme Stats表格:每支队伍平均每场比赛的表现统计;
Opponent Per Game Stats表格:所遇到的对手平均每场比赛的统计信息,所包含的统计数据与 Team Per Game Stats 中的一致,只是代表的是该球队对应的对手的统计信息;
Miscellaneous Stats:综合统计数据。

Team Per Game Stats表格、Opponent Per Game Stats表格、Miscellaneous Stats表格(在NBA网站中叫做“Advanced Stats”)中的数据字段含义如下图所示。
在这里插入图片描述
在这里插入图片描述
除了上述的三张表外,还需要另外两张表数据,分别是:
2015-2016 NBA Schedule and Results:2015-2016 年的 NBA 常规赛及季后赛的每场比赛的比赛数据;2016-2017 NBA Schedule and Results 中 2016-2017 年的 NBA 的常规赛比赛安排数据。

在获取到数据之后,需要对表格的字段做出更改如下图所示。
表格数据字段含义说明:Vteam: 客场作战队伍。Hteam: 主场作战队伍

故综上所述一共需要5张NBA数据表。如下图所示。
在这里插入图片描述

2、数据分析原理

在获取到五个表格数据之后,将利用每支队伍过去的比赛情况和 Elo 等级分来分析每支比赛队伍的胜利概率。

分析与评价每支队伍过去的比赛表现时,将使用到上述五张表中的三张表,分别是 Team Per Game Stats、Opponent Per Game Stats 和 Miscellaneous Stats(后文中将简称为 T、O 和 M 表)。

这三个表格的数据,作为代表比赛中某支队伍的比赛特征。代码将实现针对每场比赛,预测哪支队伍最终获胜,但这并不是给出绝对的胜败情况,而是预判胜利的队伍有多大的获胜概率。

因此将建立一个代表比赛的特征向量。由两支队伍的以往比赛统计情况(T、O 和M表)和两个队伍各自的 Elo 等级分构成。

3、Elo Score等级分制度

Elo 机制现在广泛运用于网络游戏或竞技类运动中,根据Elo等级分制度对各个选手(玩家)进行登记划分。如王者荣耀、篮球、足球比赛等等。Elo Score等级分制度本身是国际象棋中基于统计学的一个评估棋手水平能力的方法。

通过Elo制度来计算选手(玩家)的胜率期望值的原理过程如下:

假设A与B当前的等级制度分为与,那么A对B的胜率期望值为:

在这里插入图片描述
B对A的胜率期望值为:

在这里插入图片描述
如果A在比赛中真实得分与他的胜率期望值不同,那么A的等级分要根据以下公式进行调整:

在这里插入图片描述
另外在国际象棋中,根据等级分的不同 K 值也会做相应的调整:大于等于2400,K=16,2100-2400 分,K=24,小于等于2100,K=32。

在项目中,将会用以表示某场比赛数据的特征向量为:

[A队 Elo score,A队的 T,O和M 表统计数据,B队 Elo score, B队的 T,O和M 表统计数据]。

4、机器学习

对于全部队伍,在最开始没有Elo分数时,赋予初始值init_elo=1600。然后根据数据计算每支球队Elo等级分。代码如下图所示:

在这里插入图片描述
而后根据数据表中的数据,及每支队伍的Elo计算结果,建立对应的2015-2016年常规赛和季后赛中每场比赛的数据集。因为NBA中有主客场制度,所以在比赛时,认为主场作战的队伍更加有优势,因此会在代码中加上100的等级分。

在这里插入图片描述
而后在main函数调用上述函数方法,且使用sklearn的Logistic Regression方法建立回归模型。

Logistic Regression(逻辑回归)方法:
逻辑回归:一种用于解决二分类(0 or 1)问题的机器学习方法,用于估计某种事物的可能性。比如某用户购买某商品的可能性等。简单的来说,就是学习我们设计好的向量数据,从中得到一个概率模型,然后输入其他数据,就能根据训练出来的模型得到其结果。

接着使用通过10折交叉验证计算训练正确率。
10折交叉验证(10-fold cross validation):

常用的测试方法。将数据集分成十分,轮流将其中9份作为训练数据,1份作为测试数据,进行试验。每次试验都会得出相应的正确率(或差错率)。10次的结果的正确率(或差错率)的平均值作为对算法精度的估计,一般还需要进行多次10折交叉验证(例如10次10折交叉验证),再求其均值,作为对算法准确性的估计。

最后使用训练好的模型在2016-2017年的常规赛数据中进行预测。导入16-17数据,就可以利用模型对一场新的比赛进行胜负的判断,并且返回胜率的概率。

五、项目实施

在原网站的教程中,需要将网页的数据复制下来到txt文本上然后更改后缀名为.csv格式,比较繁琐。

在课程设计中,我更新为以爬虫获取数据,这里以爬取Team Per Game表代码为例,更改爬虫代码中的url代码部分,运行即可爬取对应赛季的Team Per Ganme Stats(各球队每场比赛数据统计)、Opponent Per Game Stats(对手平均平常比赛的数据统计)表格。而后将会自动将爬取的表格输出为.csv文件在爬虫代码的同路径下。
在这里插入图片描述
在“NBA-nwz.py”代码中,设置好全部数据文件的folder路径。如下图所示。(图片中的py文件名为test.py)然后运行代码,即可获得预测结果导出了。

在这里插入图片描述
在导出的文件prediction of 2016-2017中可以看到如下预测数据。

在这里插入图片描述

在这里插入图片描述

六、项目总结

1、实验过程问题总结

在写代码的时候,有一个包一直下载不了,各种报错,根据网上的方法找了一个小时左右,试了很多种方法才解决掉。在这里记录一下。起因就是这个parsel包import不了,一直会报同一个错误:在这里插入图片描述
CondaHTTPError:HTTP 000 CONNECTION FAILED for url
https://mirrors.tuna.tsinghua.edu.cn/anaconda/.
应该是最开始自己安装python环境的时候使用的anaconda没有配置好,或者说这个源不起作用了,于是首先尝试了第一种方法找到.condarc文件,更改里面的channels通道地址。但是当我根据网上的指导教程换国科大、阿里等信号源后依然出现错误。

后面找到了一篇文章,说是需要将https://改为 http即可,刚看到的时候以为不是这个问题,后面实在是没办法了,被这个问题搞得头大,一个多小时了卡着,只好死马当活马医,更改了一下https为http,并配入了清华源的最新配置channels,没想到解决了!

可以通过cmd命令 conda info查看自己的channels路径配置。

在这里插入图片描述
也可以通过在.condarc文件直接更改即可。进行如下配置即可轻松拥有速度较快的安装包速度了!

在这里插入图片描述

2、项目展望

总的来说,项目还是有一些小不足和继续优化的,例如在5张表中,爬下来就可以立即使用的只有三张表,分别是 Team Per Game Stats、Opponent Per Game Stats 和 Miscellaneous Stats。另外爬下来的表格需要进行字段处理,去掉不需要的字段,并且更改字段名等才能使用。而Python中是可以做到自动化处理数据字段的。这一点没有较好的实现。

除此之外,还可以使用Python可视化来做到更好的展示出比赛中两个队哪个胜率更高,
这一点我曾尝试过,但是由于效果并不是很完美,就没有放到设计项目中来。

以及在10折交叉验证中,可以看出正确率接近70%左右,感觉还可以在机器学习及数据处理(选用数据)方面再下一些功夫,达到更高的正确率。

在这里插入图片描述
因为机器学习是我自己课余时间学习过一点点的小教程,所以了解接触并不是很深,做的并不是特别完善,有机会可以多更改,进一步完善优化。

附录:全部代码

进行预测的代码:

import pandas as pd
import math
import numpy as np
import csv
from sklearn import linear_model
from sklearn.model_selection import cross_val_score

init_elo = 1600 # 初始化elo值
team_elos = {}
folder = 'D:\pydzy\py-n'  # 文件路径

def PruneData(M_stat, O_stat, T_stat):
    #这个函数要完成的任务在于将原始读入的诸多队伍的数据经过修剪,使其变为一个以team为索引的排列的特征数据
    #丢弃与球队实力无关的统计量
    pruneM = M_stat.drop(['Rk', 'Arena'],axis = 1)
    pruneO = O_stat.drop(['Rk','G','MP'],axis = 1)
    pruneT = T_stat.drop(['Rk','G','MP'],axis = 1)
    
    #将多个数据通过相同的index:team合并为一个数据
    mergeMO = pd.merge(pruneM, pruneO, how = 'left', on = 'Team')
    newstat = pd.merge(mergeMO, pruneT,  how = 'left', on = 'Team')
    
    #将team作为index的数据返回
    return newstat.set_index('Team', drop = True, append = False)

def GetElo(team):
    # 初始化每个球队的elo等级分
    try:
        return team_elos[team]
    except:
        team_elos[team] = init_elo
    return team_elos[team]

def CalcElo(winteam, loseteam):
    # winteam, loseteam的输入应为字符串
    # 给出当前两个队伍的elo分数
    R1 = GetElo(winteam)
    R2 = GetElo(loseteam)
    # 计算比赛后的等级分,参考elo计算公式
    E1 = 1/(1 + math.pow(10,(R2 - R1)/400))
    E2 = 1/(1 + math.pow(10,(R1 - R2)/400))
    if R1>=2400:
        K=16
    elif R1<=2100:
        K=32
    else:
        K=24
    R1new = round(R1 + K*(1 - E1))
    R2new = round(R2 + K*(0 - E2))
    return R1new, R2new

def GenerateTrainData(stat, trainresult):
    #将输入构造为[[team1特征,team2特征],...[]...]
    X = []
    y = []
    for index, rows in trainresult.iterrows():
        winteam = rows['WTeam']
        loseteam = rows['LTeam']
        #获取最初的elo或是每个队伍最初的elo值
        winelo = GetElo(winteam)
        loseelo = GetElo(loseteam)
        # 给主场比赛的队伍加上100的elo值
        if rows['WLoc'] == 'H':
            winelo = winelo+100
        else:
            loseelo = loseelo+100
        # 把elo当为评价每个队伍的第一个特征值
        fea_win = [winelo]
        fea_lose = [loseelo]
        # 添加我们从basketball reference.com获得的每个队伍的统计信息
        for key, value in stat.loc[winteam].iteritems():
            fea_win.append(value)
        for key, value in stat.loc[loseteam].iteritems():
            fea_lose.append(value)
        # 将两支队伍的特征值随机的分配在每场比赛数据的左右两侧
        # 并将对应的0/1赋给y值        
        if np.random.random() > 0.5:
            X.append(fea_win+fea_lose)
            y.append(0)
        else:
            X.append(fea_lose+fea_win)
            y.append(1)
        # 更新team elo分数
        win_new_score, lose_new_score = CalcElo(winteam, loseteam)
        team_elos[winteam] = win_new_score
        team_elos[loseteam] = lose_new_score
    # nan_to_num(x)是使用0代替数组x中的nan元素,使用有限的数字代替inf元素
    return np.nan_to_num(X),y
        
def GeneratePredictData(stat,info):
    X=[]
    #遍历所有的待预测数据,将数据变换为特征形式
    for index, rows in stat.iterrows():
        
        #首先将elo作为第一个特征
        team1 = rows['Vteam']
        team2 = rows['Hteam']
        elo_team1 = GetElo(team1)
        elo_team2 = GetElo(team2)
        fea1 = [elo_team1]
        fea2 = [elo_team2+100]
        #球队统计信息作为剩余特征
        for key, value in info.loc[team1].iteritems():
            fea1.append(value)
        for key, value in info.loc[team2].iteritems():
            fea2.append(value)
        #两队特征拼接
        X.append(fea1 + fea2)
    #nan_to_num的作用:1将列表变换为array,2.去除X中的非数字,保证训练器读入不出问题
    return np.nan_to_num(X)

if __name__ == '__main__':
    # 设置导入数据表格文件的地址并读入数据
    M_stat = pd.read_csv(folder + '/15-16Miscellaneous_Stat.csv')
    O_stat = pd.read_csv(folder + '/15-16Opponent_Per_Game_Stat.csv')
    T_stat = pd.read_csv(folder + '/15-16Team_Per_Game_Stat.csv')
    team_result = pd.read_csv(folder + '/2015-2016_result.csv')
    
    teamstat = PruneData(M_stat, O_stat, T_stat)
    X,y = GenerateTrainData(teamstat, team_result)

    # 训练网格模型
    limodel = linear_model.LogisticRegression()
    limodel.fit(X,y)

    # 10折交叉验证
    print(cross_val_score(model, X, y, cv=10, scoring='accuracy', n_jobs=-1).mean())

    # 预测
    pre_data = pd.read_csv(folder + '/16-17Schedule.csv')
    pre_X = GeneratePredictData(pre_data, teamstat)
    pre_y = limodel.predict_proba(pre_X)
    predictlist = []
    for index, rows in pre_data.iterrows():
        reslt = [rows['Vteam'], pre_y[index][0], rows['Hteam'], pre_y[index][1]]
        predictlist.append(reslt)
    
    # 将预测结果输出保存为csv文件
    with open(folder+'/prediction of 2016-2017.csv', 'w',newline='') as f:
        writers = csv.writer(f)
        writers.writerow(['Visit Team', 'corresponding probability of winning', 'Home Team', 'corresponding probability of winning'])
        writers.writerows(predictlist)

爬虫代码:

import requests
import re
import csv
from parsel import Selector

class NBASpider:

    def __init__(self):
        self.url = "https://www.basketball-reference.com/leagues/NBA_2021.html"
        self.schedule_url = "https://www.basketball-reference.com/leagues/NBA_2016_games-{}.html"
        self.advanced_team_url = "https://www.basketball-reference.com/leagues/NBA_2016.html"
        self.headers = {
            "User-Agent": "Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/65.0.3325.181 "
                          "Safari/537.36"
        }

    # 发送请求,获取数据
    def send(self, url):
        response = requests.get(url, headers=self.headers, timeout=30)
        response.encoding = 'utf-8'
        return response.text

    # 解析html
    def parse(self, html):
        team_heads, team_datas = self.get_team_info(html)
        opponent_heads, opponent_datas = self.get_opponent_info(html)
        return team_heads, team_datas, opponent_heads, opponent_datas

    def get_team_info(self, html):
        """
        通过正则从获取到的html页面数据中team表的表头和各行数据
        :param html 爬取到的页面数据
        :return: team_heads表头
                 team_datas 列表内容
        """
        # 1. 正则匹配数据所在的table
        team_table = re.search('<table.*?id="per_game-team".*?>(.*?)</table>', html, re.S).group(1)
        # 2. 正则从table中匹配出表头
        team_head = re.search('<thead>(.*?)</thead>', team_table, re.S).group(1)
        team_heads = re.findall('<th.*?>(.*?)</th>', team_head, re.S)
        # 3. 正则从table中匹配出表的各行数据
        team_datas = self.get_datas(team_table)

        return team_heads, team_datas

    # 解析opponent数据
    def get_opponent_info(self, html):
        """
        通过正则从获取到的html页面数据中opponent表的表头和各行数据
        :param html 爬取到的页面数据
        :return:
        """
        # 1. 正则匹配数据所在的table
        opponent_table = re.search('<table.*?id="per_game-opponent".*?>(.*?)</table>', html, re.S).group(1)
        # 2. 正则从table中匹配出表头
        opponent_head = re.search('<thead>(.*?)</thead>', opponent_table, re.S).group(1)
        opponent_heads = re.findall('<th.*?>(.*?)</th>', opponent_head, re.S)
        # 3. 正则从table中匹配出表的各行数据
        opponent_datas = self.get_datas(opponent_table)

        return opponent_heads, opponent_datas

    # 获取表格body数据
    def get_datas(self, table_html):
        """
        从tboday数据中解析出实际数据(去掉页面标签)
        :param table_html 解析出来的table数据
        :return:
        """
        tboday = re.search('<tbody>(.*?)</tbody>', table_html, re.S).group(1)
        contents = re.findall('<tr.*?>(.*?)</tr>', tboday, re.S)
        for oc in contents:
            rk = re.findall('<th.*?>(.*?)</th>', oc)
            datas = re.findall('<td.*?>(.*?)</td>', oc, re.S)
            datas[0] = re.search('<a.*?>(.*?)</a>', datas[0]).group(1)
            datas.insert(0, rk[0])
            # yield 声明这个方法是一个生成器, 返回的值是datas
            yield datas

    def get_schedule_datas(self, table_html):
        """
        从tboday数据中解析出实际数据(去掉页面标签)
        :param table_html 解析出来的table数据
        :return:
        """
        tboday = re.search('<tbody>(.*?)</tbody>', table_html, re.S).group(1)
        contents = re.findall('<tr.*?>(.*?)</tr>', tboday, re.S)
        for oc in contents:
            rk = re.findall('<th.*?><a.*?>(.*?)</a></th>', oc)
            datas = re.findall('<td.*?>(.*?)</td>', oc, re.S)
            if datas and len(datas) > 0:
                datas[1] = re.search('<a.*?>(.*?)</a>', datas[1]).group(1)
                datas[3] = re.search('<a.*?>(.*?)</a>', datas[3]).group(1)
                datas[5] = re.search('<a.*?>(.*?)</a>', datas[5]).group(1)

            datas.insert(0, rk[0])
            # yield 声明这个方法是一个生成器, 返回的值是datas
            yield datas

    def get_advanced_team_datas(self, table):
        trs = table.xpath('./tbody/tr')
        for tr in trs:
            rk = tr.xpath('./th/text()').get()
            datas = tr.xpath('./td[@data-stat!="DUMMY"]/text()').getall()
            datas[0] = tr.xpath('./td/a/text()').get()
            datas.insert(0, rk)
            yield datas

    def parse_schedule_info(self, html):
        """
        通过正则从获取到的html页面数据中的表头和各行数据
        :param html 爬取到的页面数据
        :return: heads表头
                 datas 列表内容
        """
        # 1. 正则匹配数据所在的table
        table = re.search('<table.*?id="schedule" data-cols-to-freeze=",1">(.*?)</table>', html, re.S).group(1)
        table = table + "</tbody>"
        # 2. 正则从table中匹配出表头
        head = re.search('<thead>(.*?)</thead>', table, re.S).group(1)
        heads = re.findall('<th.*?>(.*?)</th>', head, re.S)
        # 3. 正则从table中匹配出表的各行数据
        datas = self.get_schedule_datas(table)

        return heads, datas

    def parse_advanced_team(self, html):
        """
        通过xpath从获取到的html页面数据中表头和各行数据
        :param html 爬取到的页面数据
        :return: heads表头
                 datas 列表内容
        """

        selector = Selector(text=html)
        # 1. 获取对应的table
        table = selector.xpath('//table[@id="advanced-team"]')
        # 2. 从table中匹配出表头
        res = table.xpath('./thead/tr')[1].xpath('./th/text()').getall()
        heads = []
        for i, head in enumerate(res):
            if '\xa0' in head:
                continue
            heads.append(head)
        # 3. 匹配出表的各行数据
        table_data = self.get_advanced_team_datas(table)
        return heads, table_data

    # 存储成csv文件
    def save_csv(self, title, heads, rows):
        f = open(title + '.csv', mode='w', encoding='utf-8', newline='')
        csv_writer = csv.writer(f)
        csv_writer.writerow(heads)
        for row in rows:
            csv_writer.writerow(row)

        f.close()

    def crawl_team_opponent(self):
        # 1. 发送请求
        res = self.send(self.url)
        # 2. 解析数据
        team_heads, team_datas, opponent_heads, opponent_datas = self.parse(res)
        # 3. 保存数据为csv
        self.save_csv("team", team_heads, team_datas)
        self.save_csv("opponent", opponent_heads, opponent_datas)

    def crawl_schedule(self):
        months = ["october", "november", "december", "january", "february", "march", "april", "may", "june"]
        for month in months:
            html = self.send(self.schedule_url.format(month))
            # print(html)
            heads, datas = self.parse_schedule_info(html)
            # 3. 保存数据为csv
            self.save_csv("schedule_"+month, heads, datas)

    def crawl_advanced_team(self):
        # 1. 发送请求
        res = self.send(self.advanced_team_url)
        # 2. 解析数据
        heads, datas = self.parse_advanced_team(res)
        # 3. 保存数据为csv
        self.save_csv("advanced_team", heads, datas)

    def crawl(self):
        # 1. 爬取各队伍信息
        # self.crawl_team_opponent()
        # 2. 爬取计划表
        # self.crawl_schedule()
        # 3. 爬取Advanced Team表
        self.crawl_advanced_team()

if __name__ == '__main__':
    # 运行爬虫
    spider = NBASpider()
    spider.crawl()

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

Python课程设计大作业:获取比赛数据并进行机器学习智能预测NBA的比赛结果 的相关文章

  • STC89C52RC/RD中定时器2的使用方法

    学过一段时间单片机的你发现 xff0c 中断服务函数可以在主函数进行的同时 xff0c 进行一些对时间要求高的模块的配置时 xff0c 则要用到定时器中断 而如果你要实现多个功能的操作 xff0c 会使用多个定时器是必要的STC89C51单
  • keilC51中调试的方法(主要介绍串口调试XCOM)

    在keilC51中调试的方法的方法有很多 xff1a 1 直接看现象 2 串口调试 3 debug调试 下面终点讲串口调试 xff1a 若要实现printf重定向 重写printf调用的putchar函数 xff0c 重定向到串口输出 需要
  • data/xdata/pdata/code

    dada最大在128byte xff0c 不然就会报错 data xdada最大在512byte xff0c 不然就会报错 xdata pdata stc89c52中未使用 code xff08 将ROM内的定值存在程序存储器中 xff0c
  • 基于PID算法(python)的飞控设计学习日志(一)

    PID算法基础 首先我们需要去了解PID算法的数学原理 xff0c 数学原理部分借鉴于 64 确定有穷自动 机 的博客 一文读懂PID控制算法 xff08 抛弃公式 xff0c 从原理上真正理解PID控制 xff09 总的来说 xff0c
  • JAVA- 浅谈==与equal()的区别

    目录 gt 基础 gt 基本数据类型 gt 引用数据类型 gt Java内存 gt 区别 61 61 和equals gt 61 61 gt equals gt 总结 gt 基础 要想区分这两者 xff0c 我们得先明白什么是基本数据类型和
  • Ubuntu20.04+RealSense D455

    Ubuntu20 04装RealSense D455的驱动 Ubuntu20 04装RealSense D455的驱动 官网链接和个人链接 官网链接和个人链接 前言 xff1a 这些是我ubuntu20 04安装时候所找到的方法 xff0c
  • 【Java开发】 Mybatis-Plus 04:条件构造器-wrapper

    条件构造器算是Mybatis Plus中很重要的知识点了 xff0c 个人觉得它类似于Service的链式查询 xff0c 将诸多条件集中在一个wrapper中 xff0c 以达到高效便捷的目的 本文也是对01 02 03 内容的整合归纳
  • PrusaSlicer2.5中文说明1(新手篇)

    下载PrusaSlicer 稳定版本 PrusaSlicer的最新稳定版本始终可以在DRIVERS amp APPS包中找到 xff0c 它适用于Windows Mac OS X和Linux 该软件包还包括测试对象和打印机驱动程序 xff0
  • ROS机器人开发学习记录2——通过opencv读入本地图像并显示

    使用opencv和ros实现彩色图的读入和显示 为了实现该功能 xff0c 我使用了以下主要函数 xff0c 先对这些函数的功能做简要记录 xff1a xff08 1 xff09 Mat obj 61 imread 本地图像路径 实例 F
  • python中函数的参数分类

    python中函数的参数 形参 xff1a 定义函数时代表函数的形式参数 实参 xff1a 调用函数时传入的实际参数 列如 xff1a def f x y x y形参 print x y f 1 2 1 2 实参 定义函数时 xff0c 形
  • 信号量(sem)控制访问有限共享资源的线程数

    信号量 sem t就是个资源计数器 xff0c 用于控制访问有限共享资源的线程数 span class token macro property span class token directive keyword include span
  • 不需要各种代码的MATLAB语法高亮的设置,简单实用

    文章目录 前言一 代码高亮是什么 xff1f 二 设置步骤1 点击主页再点击预设2 点击MATLAB再点击颜色别着急因为是窗口太小哦所以要放大取消使用系统颜色 xff0c 然后自己选择文本颜色和背景颜色 总结 前言 这次主要想说说MATLA
  • 优先级队列(堆)

    优先级队列 1 什么是优先级队列2 什么时候用它什么时候不用它3 它的具体用法记得import两个库 xff1a 3 1定义3 2输入输出 1 什么是优先级队列 优先级队列就是用库内已有的类 xff0c 这个类名字是队列 xff0c 其实不
  • 2.1 关系模型的基本概念

    文章目录 2 1 1 基本术语定义2 1 用二维表格表示实体集 xff0c 用关键码表示实体间联系的数据模型称为关系模型 xff08 relational Model xff09 在关系模型中 xff0c 关键码 key 简称键 由一个或多
  • 2.2 关系代数的五个基本操作

    文章目录 前言2 2 关系代数2 2 1 关系代数的五个基本操作 1 投影 xff08 Projection xff09 2 选择 xff08 Selection xff09 选择与投影组合 3 xff09 并 xff08 Union xf
  • web的一些介绍

    文章目录 前言一 什么是Web xff1f 二 基本Web服务结构软件编程体系C S xff08 Client Server xff09 软件体系结构B S xff08 Brower Server xff09 软件体系结构C S结构与B S
  • .net技术第一章

    文章目录 NETC C Sharp 的特点C 的应用范围 NET Framework1 2 创建简单的C 程序结构和书写规则类型的声明和使用类型的声明和使用命名空间使用方法命名空间举例 注释Main方法命令行参数Main返回值 控制台输入和
  • .net----委托和事件

    委托和事件 委托声明实例化调用将类型安全的函数指针 方法 作为其他方法的参数进行传递 xff0c 从而实现函数回调方法委托 xff1a 匿名方法委托 多播委托委托 xff1a 委托的异步调用委托 xff1a 委托的兼容性 事件事件实际上是委
  • .net-----语言集成查询LINQ

    语言集成查询LINQ 前言相关语言要素初始值设定项匿名类型相关语言要素Lambda表达式扩展方法 LINQ的概念和基本操作集成语言查询LINQLINQ查询操作 标准查询运算符数据排序数据筛选数据投影数据分组联接运算数据分区限定运算聚合运算集
  • .net-----Windows 窗体应用程序包括控件,对话框,多重窗体,绘制图形,菜单和工具栏

    目录 前言Windows窗体应用程序概述 xff1b 窗体和大部分控件常用的事件创建Windows窗体应用程序使用Visual Studio集成开发环境实现Hello World程序 使用常用Windows窗体控件 xff1b Label

随机推荐

  • python字符串内建函数

    在八进制数前面显示零 0 xff0c 在十六进制前面显示 0x 或者 0X 取决于用的是 x 还是 X 0 显示的数字前面填充 0 而不是默认的空格 输出一个单一的 var 映射变量 字典参数 m n m 是显示的最小总宽度 n 是小数点后
  • 物理层-计算机网络速成

    物理层 1 物理层的基本概念1 1四大特性机械特性电气特性功能特性过程特性 1 2两种信号1 3 调制编码调制编码区别 1 4 传输介质双绞线光纤同轴电缆 xff1a 淘汰 xff0c 有线电话无线 xff1a IEEE802 11 1 5
  • 考研第一天,汤家凤基础班,连续与极限复习笔记

    函数连续极限 性质保号性证明极值点 xff1a 夹逼准则二项式展开根号下 xff0c 大于一 xff0c 小于一的讨论直接放缩求和分子分母齐次 xff0c 且分母大一次 xff0c 用积分 单调有界存在极限几个重要的切线放缩证明有界 xff
  • Ubuntu双系统安装教程

    安装Ubuntu双系统 1 下载Ubuntu镜像源文件2 下载制作U盘启动工具3 磁盘分区4 安装Ubuntu 1 下载Ubuntu镜像源文件 18 04 6链接 xff1a http mirrors aliyun com ubuntu r
  • Arduino造轮子—红外遥控器

    今天练习的程序是实现红外遥控器的控制 xff0c 首先 xff0c 通过太极创客的视频来看看最终的实现结果 xff1a 太极创客 零基础入门学用Arduino 第三部分 智能应用篇 合辑 本次程序例程来自太极创客官网 xff0c 此平台的A
  • 嵌入式软件刷题日记【第一天】

    1 什么是同步IO xff0c 什么是异步IO 同步就是在发出一个功能调用时 xff0c 会一直阻塞等地结果 异步就是在发出一个功能调用时 xff0c 无需阻塞等待结果 xff0c 当结果产生一般通过状态 xff0c 回调等方法来通知调用者
  • 嵌入式软件刷题笔记【第四天】

    1 头文件的两种包含形式的区别 xff1f lt gt 尖括号形式表示引用系统编译器类库路径里面的头文件 34 34 双引号则表示引用当前文件工作目录相对路径里面的头文件 2 STM32 中断是怎么进入到中断服务程序的 xff1f STM3
  • 嵌入式软件刷题【第五天】

    1 在请求分页式存储管理中 xff0c 假设一次内存访问时间为 100ns xff0c 一次快表 xff08 TLB xff09 访问时间为 20ns xff0c 地址转换计算时的快表命中率为 80 xff0c 请计算平均有效内存访问时间为
  • OSlab

    OSlab B站链接 xff1a https www bilibili com video BV1kU4y1m7QW share source 61 copy web Linux环境实践作业 在Windows Terminal的Ubuntu
  • Linux操作命令学习笔记

    Linux操作命令学习笔记 常用操作命令 xff08 以下均严格区分大小写 xff09 查看文件以及文件夹 xff1a ls命令 ls a xff08 显示隐含文件 xff0c 如以 开头的文件 ls l 长格式输出 xff0c 和ll命令
  • JAVA与C、C++比较

    浅比较Java与C C 43 43 1 语言类型 C C 43 43 是Compiled Language xff0c 而Java兼顾了Compiled Language和Interpreted Language的特点 C C 43 43
  • python正则表达式详解

    正则表达式是一个很强大的字符串处理工具 xff0c 几乎任何关于字符串的操作都可以使用正则表达式来完成 xff0c 作为一个爬虫工作者 xff0c 每天和字符串打交道 xff0c 正则表达式更是不可或缺的技能 xff0c 正则表达式的在不同
  • Java架构师发展路线

    Java架构师发展路线 初学者学习路线 Java基础 Java MySQL JDBC JavaWeb 重点 xff1a Servlet Filter Listener Cookie amp Session 常用框架 SSM框架 Spring
  • uml图 类图的表示方式 类图中类的六种关系详解 泛化关系,实现关系,依赖关系,关联关系,聚合关系,组合关系

    类图是UML图中的一种 xff0c 我们先来了解它的定义 xff1a 类图 Class Diagram 使用出现在系统中的不同类来描述系统的静态结构 xff0c 用来描述不同的类以及它们之间的关系 目录 UML类图包含元素 xff1a 单个
  • C++语言STL库常用函数

    目录 目录 万能头文件 include 1 memset xff08 xff09 批量初始化函数 2 next prev permutation全排列函数 3 unique去重函数 4 reverse 函数 5 fill 函数 6 lowe
  • 链表的排序

    148 排序链表 你链表的头结点 head xff0c 请将其按 升序 排列并返回 排序后的链表 进阶 xff1a 你可以在 O n log n 时间复杂度和常数级空间复杂度下 xff0c 对链表进行排序吗 xff1f 示例 1 xff1a
  • Ubuntu18.04如何从英文界面更改为中文界面

    1 打开设置 2 找到设置中的语言项 xff0c 点击语言安装管理 xff0c 具体步骤如下 xff1a 3 安装完毕后 xff0c 找到汉语 xff08 中国 xff09 xff0c 把它拖动到最前面 xff0c 点击关闭即可 4 完成以
  • 关于使用WinSCP或MobaXterm远程连接虚拟机请求超时或拒绝连接的解决方案

    情况背景 xff1a 本周在部署项目到虚拟机时 xff0c 想使用WinSCP拉一个比较大的文件压缩包到虚拟机中 xff0c 但是在虚拟机创建好之后 xff0c 使用终端软件连接不上虚拟机 xff0c 提示连接超时或拒绝连接 解决方案如下
  • 解决CondaHTTPError:HTTP 000 CONNECTION FAILED for url<https://mirrors.tuna.tsinghua.edu.cn/anaconda***

    解决CondaHTTPError HTTP 000 xxx 前言1 解决方法方法一 xff1a 直接通过cmd修改方法二 xff1a 通过 condarc文件进行更改 3 一些读者反馈的方法bug解决方案与注意事项 前言 今天做项目的时候
  • Python课程设计大作业:获取比赛数据并进行机器学习智能预测NBA的比赛结果

    前言 该篇是之前遗漏的大三上的Python课程设计 刚好今天有空就补发了一篇文章 全部的代码在最后附录中 爬虫类的代码直接全部放到一起了 xff0c 读者可以自行研究 百度网盘可以私聊我进行获取 一 课程设计项目说明 该课程设计项目亮点 x