Golang image operation: learn how to perform histogram equalization and global thresholding of images
Introduction:
Image processing is a field of computer vision and image processing one of the important tasks. In practical applications, we often need to perform some image enhancement operations to improve the quality of the image or highlight certain features in the image. This article will introduce how to use Golang to perform histogram equalization and global thresholding operations on images to achieve image enhancement.
1. Histogram equalization
Histogram equalization is a commonly used image enhancement method. It enhances the contrast of the image by adjusting the grayscale distribution of the image pixels. In this method, we first calculate the cumulative histogram of the image, and then adjust the pixel values of the image based on the cumulative histogram.
The following is a simple Golang code example for implementing histogram equalization of images:
package main import ( "fmt" "image" "image/color" "image/jpeg" "os" ) func main() { // 打开图片文件 file, err := os.Open("input.jpg") if err != nil { fmt.Println(err) return } defer file.Close() // 解码图片 img, _, err := image.Decode(file) if err != nil { fmt.Println(err) return } // 计算直方图 hist := histogram(img) // 计算累积直方图 cumHist := cumulativeHistogram(hist) // 根据累积直方图对图像进行像素值调整 newImg := adjustPixels(img, cumHist) // 保存处理后的图像 outFile, err := os.Create("output.jpg") if err != nil { fmt.Println(err) return } defer outFile.Close() // 编码图像 err = jpeg.Encode(outFile, newImg, &jpeg.Options{Quality: 100}) if err != nil { fmt.Println(err) return } fmt.Println("图像处理完成!") } // 计算直方图 func histogram(img image.Image) []int { bounds := img.Bounds() w, h := bounds.Max.X, bounds.Max.Y hist := make([]int, 256) for y := 0; y < h; y++ { for x := 0; x < w; x++ { r, _, _, _ := img.At(x, y).RGBA() gray := color.Gray{uint8(r / 256)} hist[gray.Y]++ } } return hist } // 计算累积直方图 func cumulativeHistogram(hist []int) []int { cumHist := make([]int, len(hist)) cumHist[0] = hist[0] for i := 1; i < len(hist); i++ { cumHist[i] = cumHist[i-1] + hist[i] } return cumHist } // 根据累积直方图调整像素值 func adjustPixels(img image.Image, cumHist []int) image.Image { bounds := img.Bounds() w, h := bounds.Max.X, bounds.Max.Y newImg := image.NewRGBA(bounds) for y := 0; y < h; y++ { for x := 0; x < w; x++ { r, g, b, a := img.At(x, y).RGBA() gray := color.Gray{uint8(r / 256)} val := uint8(float64(cumHist[gray.Y]) / float64(w*h) * 255) newImg.Set(x, y, color.RGBA{val, val, val, uint8(a / 256)}) } } return newImg }
In the above code, we first pass the image
package The ##Decode function decodes the input image file into an object of type
image.Image. Then, we call the
histogram function to calculate the histogram of the image, and the
cumulativeHistogram function to calculate the cumulative histogram of the image. Finally, we adjust the pixel values of the image based on the cumulative histogram and save the processed image to a file using the
Encode function of the
jpeg package.
Global thresholding is a simple but effective image binarization method. It divides the pixel value of the image into two non-overlapping smooth areas, representing the target respectively. Objects and background. This method is typically applied to images with clear foreground and background differences.
package main import ( "fmt" "image" "image/color" "image/jpeg" "os" ) func main() { // 打开图片文件 file, err := os.Open("input.jpg") if err != nil { fmt.Println(err) return } defer file.Close() // 解码图片 img, _, err := image.Decode(file) if err != nil { fmt.Println(err) return } // 根据全局阈值对图像进行二值化处理 newImg := binarize(img) // 保存处理后的图像 outFile, err := os.Create("output.jpg") if err != nil { fmt.Println(err) return } defer outFile.Close() // 编码图像 err = jpeg.Encode(outFile, newImg, &jpeg.Options{Quality: 100}) if err != nil { fmt.Println(err) return } fmt.Println("图像处理完成!") } // 根据全局阈值对图像进行二值化处理 func binarize(img image.Image) image.Image { bounds := img.Bounds() w, h := bounds.Max.X, bounds.Max.Y newImg := image.NewRGBA(bounds) threshold := calculateThreshold(img) for y := 0; y < h; y++ { for x := 0; x < w; x++ { r, g, b, a := img.At(x, y).RGBA() gray := color.Gray{uint8(r / 256)} var val uint8 if gray.Y > threshold { val = 255 } else { val = 0 } newImg.Set(x, y, color.RGBA{val, val, val, uint8(a / 256)}) } } return newImg } // 根据图像的直方图计算全局阈值 func calculateThreshold(img image.Image) uint8 { hist := histogram(img) totalPixels := img.Bounds().Max.X * img.Bounds().Max.Y // 计算背景像素值的总和 var bgSum, bgCount, fgSum, fgCount int for i := 0; i < len(hist); i++ { if i <= 128 { bgSum += i * hist[i] bgCount += hist[i] } else { fgSum += i * hist[i] fgCount += hist[i] } } // 计算背景和前景的平均灰度值 bgMean := bgSum / bgCount fgMean := fgSum / fgCount // 根据背景和前景的平均灰度值计算阈值 return uint8((bgMean + fgMean) / 2) } // 计算直方图 func histogram(img image.Image) []int { bounds := img.Bounds() w, h := bounds.Max.X, bounds.Max.Y hist := make([]int, 256) for y := 0; y < h; y++ { for x := 0; x < w; x++ { r, _, _, _ := img.At(x, y).RGBA() gray := color.Gray{uint8(r / 256)} hist[gray.Y]++ } } return hist }
image package The #Decode
function decodes the input image file into an object of type image.Image
. Then, we call the calculateThreshold
function to calculate the global threshold of the image. Finally, we binarize the image based on a global threshold and save the processed image to a file using the Encode
function of the jpeg
package. Summary:
The above is the detailed content of Golang image manipulation: Learn how to perform histogram equalization and global thresholding of images. For more information, please follow other related articles on the PHP Chinese website!