主頁 > 後端開發 > python+opencv實作機器視徑訓礎技術(邊緣提取,影像濾波,邊緣檢測算子,投影,車牌字符分割)

python+opencv實作機器視徑訓礎技術(邊緣提取,影像濾波,邊緣檢測算子,投影,車牌字符分割)

2020-10-08 05:41:02 後端開發

目錄
  • 一:邊緣提取
    • 1.對影像進行閾值分割并反色
    • 2.邊緣提取
  • 二:影像濾波
    • 1.讀取原圖
    • 2.均值濾波
    • 3.中值濾波
    • 4.高斯濾波
    • 5.高斯邊緣檢測
  • 三:邊緣檢測算子
    • 1.顯示原圖
    • 2.對影像進行反色
    • 3.對影像用sobel方法進行邊緣檢測
    • 4.對影像用robert方法進行邊緣檢測
  • 四:投影
    • 1.顯示原圖
    • 2.垂直方向投影
    • 3.水平方向投影
  • 五:車牌字符分割
    • 1.讀取原圖
    • 2.灰度轉換
    • 3.反色
    • 4.閾值分割
    • 5.投影
    • 6.字符識別匹配分割

??機器視覺是人工智能正在快速發展的一個分支,簡單說來,機器視覺就是用機器代替人眼來做測量和判斷,它是一項綜合技術,包括影像處理、機械工程技術、控制、電光源照明、光學成像、傳感器、模擬與數字視頻技術、計算機軟硬體技術(影像增強和分析演算法、影像卡、 I/O卡等),

??下面介紹一些機器視覺的基礎方法,用到的技術是python+opencv,python是一種很方便的高級編程語言,代碼量少,而OpenCV是一個基于BSD許可發行的跨平臺計算機視覺庫,可以運行在Linux、Windows、Android和Mac OS作業系統上,它輕量級而且高效——由一系列 C 函式和少量 C++ 類構成,同時提供了Python、Ruby、MATLAB等語言的介面,實作了影像處理和計算機視覺方面的很多通用演算法,

一:邊緣提取

??在機器視覺中,一個非常基礎的操作就是影像處理,而在影像處理中有一個十分重要的知識就是邊緣提取,邊緣提取,指數字影像處理中,對于圖片輪廓的一個處理,對于邊界處,灰度值變化比較劇烈的地方,就定義為邊緣,也就是拐點,拐點是指函式發生凹凸性變化的點,和高數的導數有聯系,將某個指定的物體的邊緣進行提取出來,而用python+opencv可以很方便地進行邊緣提取操作,

??步驟如下:

1.對影像進行閾值分割并反色

??首先需要新建一個python檔案,匯入cv2的庫(OpenCV2的python庫),并顯示一張圖片,代碼為:

import cv2

# 讀取本相對路徑下的initial.bmp檔案
image = cv2.imread ("initial.bmp")  
# 將image對應影像在影像視窗顯示出來
cv2.imshow('initial',image)
# waitKey使視窗保持靜態直到用戶按下一個鍵
cv2.waitKey(0)

??對影像進行閾值分割,閾值設定為80,得到二值化灰度圖,代碼為:

# 對影像進行閾值分割,閾值設定為80,得到二值化灰度圖
ret,image1 = cv2.threshold(image,80,255,cv2.THRESH_BINARY)
cv2.imshow('grayscale',image1)

??將影像進行反色,代碼如下:

image2 = image1.copy()		# 復制圖片
for i in range(0,image1.shape[0]):	#image.shape表示影像的尺寸和通道資訊(高,寬,通道)
for j in range(0,image1.shape[1]):
	image2[i,j]= 255 - image1[i,j]
cv2.imshow('colorReverse',image2)

2.邊緣提取

??下面就是邊緣提取了,用findContours差影法或者Canny方法檢測邊緣,用原影像減去腐蝕后的收縮影像,提取邊緣,代碼如下:

# 邊緣提取
img = cv2.cvtColor(image2,cv2.COLOR_BGR2GRAY)
canny_img_one = cv2.Canny(img,300,150)
canny_img_two = canny_img_one.copy()	# 復制圖片
for i in range(0,canny_img_one.shape[0]):	#image.shape表示影像的尺寸和通道資訊(高,寬,通道)
	for j in range(0,canny_img_one.shape[1]):
		canny_img_two[i,j]= 255 - canny_img_one[i,j]
cv2.imshow('edge',canny_img_two)

??最終我們就可以得到一個邊緣提取后的圖形,如下:

二:影像濾波

??影像濾波,即在盡量保留影像細節特征的條件下對目標影像的噪聲進行抑制,是影像預處理中不可缺少的操作,其處理效果的好壞將直接影響到后續影像處理和分析的有效性和可靠性,

??噪聲就是由于成像系統、傳輸介質和記錄設備等的不完善,數字影像在其形成、傳輸記錄程序中或者在影像處理的某些環節當輸入的像物件并不如預想時受到的污染,

??而影像濾波有很多種濾波方式,本次實驗采用的濾波方式是均值濾波,中值濾波和高斯濾波,以及高斯邊緣檢測,

??均值濾波是典型的線性濾波演算法,它是指在影像上對目標像素給一個模板,該模板包括了其周圍的臨近像素(以目標像素為中心的周圍8個像素,構成一個濾波模板,即去掉目標像素本身),再用模板中的全體像素的平均值來代替原來像素值,

??中值濾波是基于排序統計理論的一種能有效抑制噪聲的非線性信號處理技術,中值濾波的基本原理是把數字影像或數字序列中一點的值用該點的一個鄰域中各點值的中值代替,讓周圍的像素值接近的真實值,從而消除孤立的噪聲點,

??高斯濾波是一種線性平滑濾波,適用于消除高斯噪聲,廣泛應用于影像處理的減噪程序,高斯濾波就是對整幅影像進行加權平均的程序,每一個像素點的值,都由其本身和鄰域內的其他像素值經過加權平均后得到,

??邊緣檢測的目的是標識數字影像中亮度變化明顯的點,高斯邊緣檢測是用高斯濾波的方式進行邊緣檢測,

??步驟如下:

1.讀取原圖

??首先展示原圖,代碼如下:

import cv2
import cv2 as cv

# 讀取本相對路徑下的initial.bmp檔案
image = cv2.imread ("initial.png")
# 加入文本資訊
cv2.putText(image,'initial',(50,50),cv2.FONT_HERSHEY_SIMPLEX,1.5,(255,0, 0),4)
# 將image對應影像在影像視窗顯示出來
cv2.imshow('initial',image)
cv2.waitKey(0)

2.均值濾波

??然后進行均值濾波,代碼如下:

# 均值濾波
image2 = cv2.blur(image,(10,5))
cv2.putText(image2,'averageFiltering',(50,50),cv2.FONT_HERSHEY_SIMPLEX,1.5,(255,0, 0),4)
cv2.imshow('averageFiltering',image2)

3.中值濾波

??然后進行中值濾波,代碼如下:

image3 = cv2.medianBlur(image, 5)
cv2.putText(image3,'medianFiltering',(50,50),cv2.FONT_HERSHEY_SIMPLEX,1.5,(255,0, 0),4)
cv2.imshow('medianFiltering',image3)

4.高斯濾波

??之后進行高斯濾波,代碼如下:

# 高斯濾波
image4 = cv2.GaussianBlur(image,(5,5),0)
cv2.putText(image4,'gaussianFilter',(50,50),cv2.FONT_HERSHEY_SIMPLEX,1.5,(255,0, 0),4)
cv2.imshow('gaussianFilter',image4)

5.高斯邊緣檢測

??最終進行高斯邊緣檢測,代碼如下:

# 高斯邊緣檢測
gau_matrix = np.asarray([[-2/28,-5/28,-2/28],[-5/28,28/28,-5/28],[-2/28,-5/28,-2/28]])
img = np.zeros(image.shape)
hight,width = image.shape
for i in range(1,hight-1):
	for j in range(1,width-1):
		img[i-1,j-1] = np.sum(image[i-1:i+2,j-1:j+2]*gau_matrix)
image5 = img.astype(np.uint8)
cv2.putText(image5,'gaussianEdgeDetection',(50,50),cv2.FONT_HERSHEY_SIMPLEX,1.5,(255,0, 0),4)
cv2.imshow('gaussianEdgeDetection',image5)

三:邊緣檢測算子

??邊緣檢測是影像處理和計算機視覺中的基本問題,邊緣檢測的目的是標識數字影像中亮度變化明顯的點,包括深度上的不連續、表面方向不連續、物質屬性變化和場景照明變化等,是計算機視覺的特征提取的一個領域,

??在實際的影像分割中,往往只用到一階和二階導數,雖然原理上,可以用更高階的導數,但是因為噪聲的影響,在純粹二階的導數操作中就會出現對噪聲的敏感現象,三階以上的導數資訊往往失去了應用價值,二階導數還可以說明灰度突變的型別,在某些情況下,如灰度變化均勻的影像,只利用一階導數可能找不到邊界,此時二階導數就能提供很有用的資訊,二階導數對噪聲也比較敏感,解決的方法是先對影像進行平滑濾波,消除部分噪聲,再進行邊緣檢測,不過,利用二階導數資訊的演算法是基于過零檢測的,因此得到的邊緣點數比較少,有利于后繼的處理和識別作業,

??計算機視覺正是模仿人類視覺的這個程序,因此在檢測物體邊緣時,先對其輪廓點進行粗略檢測,然后通過鏈接規則把原來檢測到的輪廓點連接起來,同時也檢測和連接遺漏的邊界點及去除虛假的邊界點,影像的邊緣是影像的重要特征,是計算機視覺、模式識別等的基礎,因此邊緣檢測是圖象處理中一個重要的環節,

??而在opencv中也有幾個邊緣檢測方法,一階的有Roberts Cross算子,Prewitt算子,Sobel算子,Canny算子,Krisch算子,羅盤算子;而二階的還有Marr-Hildreth,在梯度方向的二階導數過零點,

??步驟如下:

1.顯示原圖

??首先用下面的代碼表現出原影像:

# 讀取本相對路徑下的dip_switch_02.bmp檔案
src_s = cv2.imread ("dip_switch_02.bmp",0)
cv2.imshow('src_s',src_s)

2.對影像進行反色

??對影像進行反色,反色是與原色疊加可以變為白色的顏色,可以用白色(RGB:255,255,255)減去原來圖片的顏色,因此對于黑白圖片,我們先加載一個8位灰度影像,每一個像素對應的灰度值從0-255,則只需要讀取每個像素的灰度值A,再將255-A寫入,這樣操作一遍后,影像就會反色了,代碼如下:

src = https://www.cnblogs.com/ITXiaoAng/p/cv.imread("dip_switch_02.bmp")
height, width, channels = src.shape
for row in range(height):
    for list in range(width):
        for c in range(channels):
            pv = src[row, list, c]
            src[row, list, c] = 255 - pv
cv.imshow("AfterDeal", src)

3.對影像用sobel方法進行邊緣檢測

??Sobel算子是一種用于邊緣檢測的離散微分算子,它結合了高斯平滑和微分求導,該算子用于計算影像明暗程度近似值,根據影像邊緣旁邊明暗程度把該區域內超過某個數的特定點記為邊緣,Sobel 算子在Prewitt算子的基礎上增加了權重的概念,認為相鄰點的距離遠近對當前像素點的影響是不同的,距離越近的像素點對應當前像素的影響越大,從而實作影像銳化并突出邊緣輪廓,

??Sobel算子的邊緣定位更準確,常用于噪聲較多,灰度漸變的影像
Sobel算子包含兩組3x3的矩陣,分別為橫向及縱向模板,將之與影像作平面卷積,即可分別得出橫向及縱向的亮度差分近似值,

??代碼如下:

# 用sobel方法進行邊緣檢測
x = cv2.Sobel(src,cv2.CV_16S,1,0)
y = cv2.Sobel(src,cv2.CV_16S,0,1)
absX = cv2.convertScaleAbs(x)   # 轉回uint8
# cv2.imshow("absX", absX)

# 截圖后反轉
def inverse_color(image):
	height, width, channels = image.shape
	for row in range(height):
			for list in range(width):
				for c in range(channels):
					pv = image[row, list, c]
					image[row, list, c] = 255 - pv

	cv.imshow("result", image)
one = cv.imread("2.jpg")
inverse_color(one)

4.對影像用robert方法進行邊緣檢測

??Roberts 算子又稱為交叉微分算子,它是基于交叉差分的梯度演算法,通過區域差分計算檢測邊緣線條,常用來處理具有陡峭的低噪聲影像,當影像邊緣接近于正 45 度或負 45 度時,該演算法處理效果更理想,其缺點是對邊緣的定位不太準確,提取的邊緣線條較粗,

# 用robert方法進行邊緣檢測
dst = cv2.addWeighted(absX,0.5,absY,0.5,0)
# cv2.imshow("dst", dst)
# 截圖后反轉
def inverse_color(image):
	height, width, channels = image.shape
	for row in range(height):
			for list in range(width):
				for c in range(channels):
					pv = image[row, list, c]
					image[row, list, c] = 255 - pv
cv.imshow("result", image)
three = cv.imread ("3.jpg")
inverse_color(three)

四:投影

??投影就是就是把一個場景投影到攝像機的像平面上,型別有透視投影,仿射投影,弱透視投影與類透視投影等,

??在opencv中,投影主要分為水平投影和垂直投影,水平投影是二維影像在y軸上的投影;垂直投影是二維影像在x軸上的投影,

??在水平和垂直的方向上進行投影,先將投影的影像轉化為灰度圖,然后進行二值化閾值分割,之后在水平和垂直的方向上進行投影,所用庫為cv2以及matplotlib資料分析庫進行操作,
??步驟如下:

1.顯示原圖

import cv2 
import numpy as np 
from matplotlib import pyplot as plt 

img=cv2.imread('123.jpg')

2.垂直方向投影

img=cv2.imread('123.jpg') #讀取圖片,裝換為可運算的陣列
GrayImage=cv2.cvtColor(img,cv2.COLOR_BGR2GRAY) #將BGR圖轉為灰度圖
ret,thresh1=cv2.threshold(GrayImage,130,255,cv2.THRESH_BINARY)#將圖片進行二值化(130,255)之間的點均變為255(背景)
(h,w)=thresh1.shape #回傳高和寬
a = [0 for z in range(0, w)] 
#記錄每一列的波峰
for j in range(0,w): #遍歷一列 
	for i in range(0,h): #遍歷一行
		if thresh1[i,j]==0: #如果改點為黑點
			a[j]+=1 #該列的計數器加一計數
			thresh1[i,j]=255 #記錄完后將其變為白色 

for j in range(0,w): #遍歷每一列
	for i in range((h-a[j]),h): #從該列應該變黑的最頂部的點開始向最底部涂黑
		thresh1[i,j]=0 #涂黑
plt.imshow(thresh1,cmap=plt.gray())
plt.show()
cv2.imshow('one',thresh1) 
cv2.waitKey(0)

3.水平方向投影

for j in range(0,h): 
	for i in range(0,w): 
		if thresh1[j,i]==0: 
			a[j]+=1 
			thresh1[j,i]=255

for j in range(0,h): 
	for i in range(0,a[j]): 
		thresh1[j,i]=0 

plt.imshow(thresh1,cmap=plt.gray())
plt.show()

五:車牌字符分割

??車牌識別系統(Vehicle License Plate Recognition,VLPR) 是計算機視頻影像識別技術在車輛牌照識別中的一種應用,

??車牌識別技術要求能夠將運動中的汽車牌照從復雜背景中提取并識別出來,通過車牌提取、影像預處理、特征提取、車牌字符識別等技術,識別車輛牌號、顏色等資訊,目前最新的技術水平為字母和數字的識別率可達到99.7%,漢字的識別率可達到99%,

??要將車牌進行字符分割,先進行字符識別操作,這里進行的是直接用方框識別并括起來,需要的步驟是首先要讓彩色的車牌影像轉化為灰度圖,再反色,閾值分割,再利用水平和垂直方向的投影依次截取需要的小方框的長和寬,進行識別,用到的技術是python+opencv其中的cv2庫以及資料分析numpy庫,
??步驟如下:

1.讀取原圖

import cv2
import cv2 as cv
import numpy as np

image1 = cv.imread('123456.jpg',1)
cv.imshow('image1', image1)

2.灰度轉換

??然后把圖片轉化為灰度圖,這里設定讀取圖片用灰度圖片讀取即可,

image2 = cv.imread('123456.jpg',0)
cv.imshow('image2', image2)

3.反色

??接著將影像進行反色,記錄寬高和深度,并用255減去灰度圖顏色的寬高,

height, width, deep = image1.shape
dst = np.zeros((height,width,1), np.uint8)
for i in range(0, height):
    for j in range(0, width):
        grayPixel = image2[i, j]
        dst[i, j] = 255-grayPixel
cv2.imshow('image3', dst)

4.閾值分割

??然后將反色后的影像進行閾值分割,閾值設為100,

ret, thresh = cv2.threshold(dst, 100, 255, cv2.THRESH_TOZERO)
cv2.imshow('image4', thresh)

5.投影

??之后在水平和垂直方向上進行投影,畫出投影圖,并記錄投影小黑點的單位起始長度陣列,設定兩個函式,回傳之后要用到的每個小分割矩形的特征點坐標值,

# 水平方向投影
def hProject(binary):
    h, w = binary.shape
    # 水平投影
    hprojection = np.zeros(binary.shape, dtype=np.uint8)
    # 創建h長度都為0的陣列
    h_h = [0]*h
    for j in range(h):
        for i in range(w):
            if binary[j,i] == 0:
                h_h[j] += 1
    # 畫出投影圖
    for j in range(h):
        for i in range(h_h[j]):
            hprojection[j,i] = 255
    return h_h

# 垂直反向投影
def vProject(binary):
    h, w = binary.shape
    # 垂直投影
    vprojection = np.zeros(binary.shape, dtype=np.uint8)
    # 創建 w 長度都為0的陣列
    w_w = [0]*w
    for i in range(w):
        for j in range(h):
            if binary[j, i ] == 0:
                w_w[i] += 1
    for i in range(w):
        for j in range(w_w[i]):
            vprojection[j,i] = 255
    return w_w

6.字符識別匹配分割

??根據回傳的陣列,確定分割位置,進行字符識別匹配分割,

th = thresh
h,w = th.shape
h_h = hProject(th)
start = 0
h_start, h_end = [], []
position = []
# 根據水平投影獲取垂直分割
for i in range(len(h_h)):
    if h_h[i] > 0 and start == 0:
        h_start.append(i)
        start = 1
    if h_h[i] ==0 and start == 1:
        h_end.append(i)
        start = 0
for i in range(len(h_start)):
    cropImg = th[h_start[i]:h_end[i], 0:w]
    if i ==0:
        pass
    w_w = vProject(cropImg)
    wstart , wend, w_start, w_end = 0, 0, 0, 0
    for j in range(len(w_w)):
        if w_w[j] > 0 and wstart == 0:
            w_start = j
            wstart = 1
            wend = 0
        if w_w[j] ==0 and wstart == 1:
            w_end = j
            wstart = 0
            wend = 1
        # 當確認了起點和終點之后保存坐標   
        if wend == 1:
            position.append([w_start, h_start[i], w_end, h_end[i]])
            wend = 0
# 確定分割位置
for p in position:
    cv2.rectangle(thresh, (p[0], p[1]), (p[2], p[3]), (0, 0, 255), 2)
cv2.imshow('image7', thresh)
cv.waitKey(0)

轉載請註明出處,本文鏈接:https://www.uj5u.com/houduan/162478.html

標籤:Python

上一篇:python自學之路

下一篇:python漢諾塔問題

標籤雲
其他(157675) Python(38076) JavaScript(25376) Java(17977) C(15215) 區塊鏈(8255) C#(7972) AI(7469) 爪哇(7425) MySQL(7132) html(6777) 基礎類(6313) sql(6102) 熊猫(6058) PHP(5869) 数组(5741) R(5409) Linux(5327) 反应(5209) 腳本語言(PerlPython)(5129) 非技術區(4971) Android(4554) 数据框(4311) css(4259) 节点.js(4032) C語言(3288) json(3245) 列表(3129) 扑(3119) C++語言(3117) 安卓(2998) 打字稿(2995) VBA(2789) Java相關(2746) 疑難問題(2699) 细绳(2522) 單片機工控(2479) iOS(2429) ASP.NET(2402) MongoDB(2323) 麻木的(2285) 正则表达式(2254) 字典(2211) 循环(2198) 迅速(2185) 擅长(2169) 镖(2155) 功能(1967) .NET技术(1958) Web開發(1951) python-3.x(1918) HtmlCss(1915) 弹簧靴(1913) C++(1909) xml(1889) PostgreSQL(1872) .NETCore(1853) 谷歌表格(1846) Unity3D(1843) for循环(1842)

熱門瀏覽
  • 【C++】Microsoft C++、C 和匯編程式檔案

    ......

    uj5u.com 2020-09-10 00:57:23 more
  • 例外宣告

    相比于斷言適用于排除邏輯上不可能存在的狀態,例外通常是用于邏輯上可能發生的錯誤。 例外宣告 Item 1:當函式不可能拋出例外或不能接受拋出例外時,使用noexcept 理由 如果不打算拋出例外的話,程式就會認為無法處理這種錯誤,并且應當盡早終止,如此可以有效地阻止例外的傳播與擴散。 示例 //不可 ......

    uj5u.com 2020-09-10 00:57:27 more
  • Codeforces 1400E Clear the Multiset(貪心 + 分治)

    鏈接:https://codeforces.com/problemset/problem/1400/E 來源:Codeforces 思路:給你一個陣列,現在你可以進行兩種操作,操作1:將一段沒有 0 的區間進行減一的操作,操作2:將 i 位置上的元素歸零。最終問:將這個陣列的全部元素歸零后操作的最少 ......

    uj5u.com 2020-09-10 00:57:30 more
  • UVA11610 【Reverse Prime】

    本人看到此題沒有翻譯,就附帶了一個自己的翻譯版本 思考 這一題,它的第一個要求是找出所有 $7$ 位反向質數及其質因數的個數。 我們應該需要質數篩篩選1~$10^{7}$的所有數,這里就不慢慢介紹了。但是,重讀題,我們突然發現反向質數都是 $7$ 位,而將它反過來后的數字卻是 $6$ 位數,這就說明 ......

    uj5u.com 2020-09-10 00:57:36 more
  • 統計區間素數數量

    1 #pragma GCC optimize(2) 2 #include <bits/stdc++.h> 3 using namespace std; 4 bool isprime[1000000010]; 5 vector<int> prime; 6 inline int getlist(int ......

    uj5u.com 2020-09-10 00:57:47 more
  • C/C++編程筆記:C++中的 const 變數詳解,教你正確認識const用法

    1、C中的const 1、區域const變數存放在堆疊區中,會分配記憶體(也就是說可以通過地址間接修改變數的值)。測驗代碼如下: 運行結果: 2、全域const變數存放在只讀資料段(不能通過地址修改,會發生寫入錯誤), 默認為外部聯編,可以給其他源檔案使用(需要用extern關鍵字修飾) 運行結果: ......

    uj5u.com 2020-09-10 00:58:04 more
  • 【C++犯錯記錄】VS2019 MFC添加資源不懂如何修改資源宏ID

    1. 首先在資源視圖中,添加資源 2. 點擊新添加的資源,復制自動生成的ID 3. 在解決方案資源管理器中找到Resource.h檔案,編輯,使用整個專案搜索和替換的方式快速替換 宏宣告 4. Ctrl+Shift+F 全域搜索,點擊查找全部,然后逐個替換 5. 為什么使用搜索替換而不使用屬性視窗直 ......

    uj5u.com 2020-09-10 00:59:11 more
  • 【C++犯錯記錄】VS2019 MFC不懂的批量添加資源

    1. 打開資源頭檔案Resource.h,在其中預先定義好宏 ID(不清楚其實ID值應該設定多少,可以先新建一個相同的資源項,再在這個資源的ID值的基礎上遞增即可) 2. 在資源視圖中選中專案資源,按F7編輯資源檔案,按 ID 型別 相對路徑的形式添加 資源。(別忘了先把檔案拷貝到專案中的res檔案 ......

    uj5u.com 2020-09-10 01:00:19 more
  • C/C++編程筆記:關于C++的參考型別,專供新手入門使用

    今天要講的是C++中我最喜歡的一個用法——參考,也叫別名。 參考就是給一個變數名取一個變數名,方便我們間接地使用這個變數。我們可以給一個變數創建N個參考,這N + 1個變數共享了同一塊記憶體區域。(參考型別的變數會占用記憶體空間,占用的記憶體空間的大小和指標型別的大小是相同的。雖然參考是一個物件的別名,但 ......

    uj5u.com 2020-09-10 01:00:22 more
  • 【C/C++編程筆記】從頭開始學習C ++:初學者完整指南

    眾所周知,C ++的學習曲線陡峭,但是花時間學習這種語言將為您的職業帶來奇跡,并使您與其他開發人員區分開。您會更輕松地學習新語言,形成真正的解決問題的技能,并在編程的基礎上打下堅實的基礎。 C ++將幫助您養成良好的編程習慣(即清晰一致的編碼風格,在撰寫代碼時注釋代碼,并限制類內部的可見性),并且由 ......

    uj5u.com 2020-09-10 01:00:41 more
最新发布
  • Rust中的智能指標:Box<T> Rc<T> Arc<T> Cell<T> RefCell<T> Weak

    Rust中的智能指標是什么 智能指標(smart pointers)是一類資料結構,是擁有資料所有權和額外功能的指標。是指標的進一步發展 指標(pointer)是一個包含記憶體地址的變數的通用概念。這個地址參考,或 ” 指向”(points at)一些其 他資料 。參考以 & 符號為標志并借用了他們所 ......

    uj5u.com 2023-04-20 07:24:10 more
  • Java的值傳遞和參考傳遞

    值傳遞不會改變本身,參考傳遞(如果傳遞的值需要實體化到堆里)如果發生修改了會改變本身。 1.基本資料型別都是值傳遞 package com.example.basic; public class Test { public static void main(String[] args) { int ......

    uj5u.com 2023-04-20 07:24:04 more
  • [2]SpinalHDL教程——Scala簡單入門

    第一個 Scala 程式 shell里面輸入 $ scala scala> 1 + 1 res0: Int = 2 scala> println("Hello World!") Hello World! 檔案形式 object HelloWorld { /* 這是我的第一個 Scala 程式 * 以 ......

    uj5u.com 2023-04-20 07:23:58 more
  • 理解函式指標和回呼函式

    理解 函式指標 指向函式的指標。比如: 理解函式指標的偽代碼 void (*p)(int type, char *data); // 定義一個函式指標p void func(int type, char *data); // 宣告一個函式func p = func; // 將指標p指向函式func ......

    uj5u.com 2023-04-20 07:23:52 more
  • Django筆記二十五之資料庫函式之日期函式

    本文首發于公眾號:Hunter后端 原文鏈接:Django筆記二十五之資料庫函式之日期函式 日期函式主要介紹兩個大類,Extract() 和 Trunc() Extract() 函式作用是提取日期,比如我們可以提取一個日期欄位的年份,月份,日等資料 Trunc() 的作用則是截取,比如 2022-0 ......

    uj5u.com 2023-04-20 07:23:45 more
  • 一天吃透JVM面試八股文

    什么是JVM? JVM,全稱Java Virtual Machine(Java虛擬機),是通過在實際的計算機上仿真模擬各種計算機功能來實作的。由一套位元組碼指令集、一組暫存器、一個堆疊、一個垃圾回收堆和一個存盤方法域等組成。JVM屏蔽了與作業系統平臺相關的資訊,使得Java程式只需要生成在Java虛擬機 ......

    uj5u.com 2023-04-20 07:23:31 more
  • 使用Java接入小程式訂閱訊息!

    更新完微信服務號的模板訊息之后,我又趕緊把微信小程式的訂閱訊息給實作了!之前我一直以為微信小程式也是要企業才能申請,沒想到小程式個人就能申請。 訊息推送平臺🔥推送下發【郵件】【短信】【微信服務號】【微信小程式】【企業微信】【釘釘】等訊息型別。 https://gitee.com/zhongfuch ......

    uj5u.com 2023-04-20 07:22:59 more
  • java -- 緩沖流、轉換流、序列化流

    緩沖流 緩沖流, 也叫高效流, 按照資料型別分類: 位元組緩沖流:BufferedInputStream,BufferedOutputStream 字符緩沖流:BufferedReader,BufferedWriter 緩沖流的基本原理,是在創建流物件時,會創建一個內置的默認大小的緩沖區陣列,通過緩沖 ......

    uj5u.com 2023-04-20 07:22:49 more
  • Java-SpringBoot-Range請求頭設定實作視頻分段傳輸

    老實說,人太懶了,現在基本都不喜歡寫筆記了,但是網上有關Range請求頭的文章都太水了 下面是抄的一段StackOverflow的代碼...自己大修改過的,寫的注釋挺全的,應該直接看得懂,就不解釋了 寫的不好...只是希望能給視頻網站開發的新手一點點幫助吧. 業務場景:視頻分段傳輸、視頻多段傳輸(理 ......

    uj5u.com 2023-04-20 07:22:42 more
  • Windows 10開發教程_編程入門自學教程_菜鳥教程-免費教程分享

    教程簡介 Windows 10開發入門教程 - 從簡單的步驟了解Windows 10開發,從基本到高級概念,包括簡介,UWP,第一個應用程式,商店,XAML控制元件,資料系結,XAML性能,自適應設計,自適應UI,自適應代碼,檔案管理,SQLite資料庫,應用程式到應用程式通信,應用程式本地化,應用程式 ......

    uj5u.com 2023-04-20 07:22:35 more