mirror of
https://github.com/glebarez/go-sqlite.git
synced 2025-10-06 00:06:56 +08:00
Go vs CGo benchmarks refactored (not TPCH)
This commit is contained in:
236
benchmark/plot.go
Normal file
236
benchmark/plot.go
Normal file
@@ -0,0 +1,236 @@
|
||||
// Copyright 2021 The Sqlite Authors. All rights reserved.
|
||||
// Use of this source code is governed by a BSD-style
|
||||
// license that can be found in the LICENSE file.
|
||||
|
||||
// helpers for plotting benchmark results
|
||||
package benchmark
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"os"
|
||||
"path"
|
||||
|
||||
"github.com/wcharczuk/go-chart"
|
||||
"github.com/wcharczuk/go-chart/drawing"
|
||||
)
|
||||
|
||||
const (
|
||||
yAxisCeilStep = 200000
|
||||
)
|
||||
|
||||
var transparentColor = drawing.ColorWhite.WithAlpha(0)
|
||||
|
||||
type GraphCompareOfNRows struct {
|
||||
// this fields should be set externally
|
||||
rowCountsE []int
|
||||
title string
|
||||
palette chart.ColorPalette
|
||||
|
||||
// this fields are for private use
|
||||
seriesNameS []string
|
||||
seriesValuesS [][]float64
|
||||
}
|
||||
|
||||
func (g *GraphCompareOfNRows) AddSeries(name string, values []float64) {
|
||||
g.seriesNameS = append(g.seriesNameS, name)
|
||||
g.seriesValuesS = append(g.seriesValuesS, values)
|
||||
}
|
||||
|
||||
func (g *GraphCompareOfNRows) Render(filename string) error {
|
||||
// new chart object
|
||||
graph := g.newGraph()
|
||||
|
||||
// generate series objects for graph
|
||||
for i, seriesName := range g.seriesNameS {
|
||||
// get corresponding series values
|
||||
seriesValues := g.seriesValuesS[i]
|
||||
|
||||
// create series object
|
||||
graph.Series = append(graph.Series, g.createSeries(seriesName, seriesValues))
|
||||
|
||||
// adjust max for Y axis
|
||||
yMax := (int(max(seriesValues...)/yAxisCeilStep) + 1) * yAxisCeilStep // a special case of ceil()
|
||||
if graph.YAxis.Range.GetMax() < float64(yMax) {
|
||||
graph.YAxis.Range = &chart.ContinuousRange{
|
||||
Min: 0,
|
||||
Max: float64(yMax),
|
||||
}
|
||||
}
|
||||
|
||||
// skip annotations for first series
|
||||
if i == 0 {
|
||||
continue
|
||||
}
|
||||
|
||||
// for every series except first, we create a ratio annotation s[X]/s[0]
|
||||
annotations := &chart.AnnotationSeries{}
|
||||
for i, v := range seriesValues {
|
||||
annotations.Annotations = append(annotations.Annotations, g.newRatioAnnotation(
|
||||
float64(g.rowCountsE[i]),
|
||||
v,
|
||||
v/g.seriesValuesS[0][i],
|
||||
))
|
||||
|
||||
}
|
||||
|
||||
// append annotations to graph
|
||||
graph.Series = append(graph.Series, annotations)
|
||||
}
|
||||
|
||||
// add legend
|
||||
graph.Elements = []chart.Renderable{
|
||||
chart.Legend(graph, chart.Style{
|
||||
FontSize: 12,
|
||||
StrokeColor: transparentColor,
|
||||
FillColor: g.palette.CanvasColor(),
|
||||
FontColor: g.palette.TextColor().WithAlpha(192),
|
||||
}),
|
||||
}
|
||||
|
||||
// write into file
|
||||
if err := os.MkdirAll(path.Dir(filename), 0775); err != nil {
|
||||
return err
|
||||
}
|
||||
f, err := os.Create(filename)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
defer f.Close()
|
||||
if err := graph.Render(chart.PNG, f); err != nil {
|
||||
return err
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func (g *GraphCompareOfNRows) createSeries(name string, values []float64) chart.Series {
|
||||
// convert E values of rowCount onto float64
|
||||
var xValues []float64
|
||||
for _, e := range g.rowCountsE {
|
||||
xValues = append(xValues, float64(e))
|
||||
}
|
||||
|
||||
// create series
|
||||
series := &chart.ContinuousSeries{
|
||||
Name: name,
|
||||
Style: chart.Style{
|
||||
DotWidth: 2.5,
|
||||
Show: true,
|
||||
StrokeWidth: 1.5,
|
||||
},
|
||||
XValues: xValues,
|
||||
YValues: values,
|
||||
}
|
||||
|
||||
// save in series slice
|
||||
return series
|
||||
}
|
||||
|
||||
func (g *GraphCompareOfNRows) newGraph() *chart.Chart {
|
||||
return &chart.Chart{
|
||||
ColorPalette: g.palette,
|
||||
Title: g.title,
|
||||
TitleStyle: chart.Style{
|
||||
Show: true,
|
||||
},
|
||||
Background: chart.Style{
|
||||
Padding: chart.Box{
|
||||
Top: 20,
|
||||
Left: 20,
|
||||
},
|
||||
},
|
||||
Canvas: chart.Style{},
|
||||
XAxis: chart.XAxis{
|
||||
Style: chart.StyleShow(),
|
||||
NameStyle: chart.StyleShow(),
|
||||
Name: "rows",
|
||||
Ticks: g.genXticks(),
|
||||
},
|
||||
YAxis: chart.YAxis{
|
||||
Range: &chart.ContinuousRange{},
|
||||
Style: chart.StyleShow(),
|
||||
Name: "rows/sec",
|
||||
NameStyle: chart.StyleShow(),
|
||||
ValueFormatter: func(v interface{}) string { return fmt.Sprintf("%.0f", v) },
|
||||
},
|
||||
}
|
||||
}
|
||||
|
||||
func (g *GraphCompareOfNRows) newRatioAnnotation(x, y, ratio float64) chart.Value2 {
|
||||
return chart.Value2{
|
||||
XValue: x,
|
||||
YValue: y,
|
||||
Label: fmt.Sprintf("%.2fx", ratio),
|
||||
Style: chart.Style{
|
||||
FontSize: 8,
|
||||
TextHorizontalAlign: chart.TextHorizontalAlignLeft,
|
||||
FillColor: transparentColor, // full tranparency
|
||||
StrokeColor: transparentColor, // full transparency
|
||||
FontColor: g.palette.TextColor().WithAlpha(255), // no transaprency
|
||||
TextRotationDegrees: 45,
|
||||
},
|
||||
}
|
||||
}
|
||||
|
||||
func (g *GraphCompareOfNRows) genXticks() []chart.Tick {
|
||||
var ticks []chart.Tick
|
||||
for i, e := range g.rowCountsE {
|
||||
ticks = append(ticks, chart.Tick{
|
||||
Value: float64(e),
|
||||
Label: fmt.Sprintf("1e%d", i+1),
|
||||
})
|
||||
}
|
||||
return ticks
|
||||
}
|
||||
|
||||
func max(f ...float64) float64 {
|
||||
if len(f) == 0 {
|
||||
return 0
|
||||
}
|
||||
m := f[0]
|
||||
for i := 1; i < len(f); i++ {
|
||||
if m < f[i] {
|
||||
m = f[i]
|
||||
}
|
||||
}
|
||||
return m
|
||||
}
|
||||
|
||||
type palette struct {
|
||||
bgColor drawing.Color
|
||||
bgStrokeColor drawing.Color
|
||||
canvasColor drawing.Color
|
||||
canvasStrokeColor drawing.Color
|
||||
axisStrokeColor drawing.Color
|
||||
textColor drawing.Color
|
||||
seriesColor []drawing.Color
|
||||
}
|
||||
|
||||
func (p *palette) BackgroundColor() drawing.Color { return p.bgColor }
|
||||
func (p *palette) BackgroundStrokeColor() drawing.Color { return p.bgStrokeColor }
|
||||
func (p *palette) CanvasColor() drawing.Color { return p.canvasColor }
|
||||
func (p *palette) CanvasStrokeColor() drawing.Color { return p.canvasStrokeColor }
|
||||
func (p *palette) AxisStrokeColor() drawing.Color { return p.axisStrokeColor }
|
||||
func (p *palette) TextColor() drawing.Color { return p.textColor }
|
||||
func (p *palette) GetSeriesColor(i int) drawing.Color { return p.seriesColor[i%len(p.seriesColor)] }
|
||||
|
||||
var DarkPalette = &palette{
|
||||
bgColor: drawing.ColorFromHex("252526"),
|
||||
canvasColor: drawing.ColorFromHex("1e1e1e1"),
|
||||
textColor: drawing.ColorFromHex("d4d4d4").WithAlpha(128),
|
||||
axisStrokeColor: drawing.ColorFromHex("d4d4d4").WithAlpha(128),
|
||||
seriesColor: []drawing.Color{
|
||||
drawing.ColorFromHex("d5d5a5"),
|
||||
drawing.ColorFromHex("569cd5"),
|
||||
},
|
||||
}
|
||||
|
||||
var LightPalette = &palette{
|
||||
canvasColor: drawing.ColorFromHex("f2f2f2"),
|
||||
bgColor: drawing.ColorFromHex("f5f5f5"),
|
||||
textColor: drawing.ColorFromHex("393939").WithAlpha(128),
|
||||
axisStrokeColor: drawing.ColorFromHex("393939").WithAlpha(128),
|
||||
seriesColor: []drawing.Color{
|
||||
drawing.ColorFromHex("aa3731"),
|
||||
drawing.ColorFromHex("5a77c7"),
|
||||
},
|
||||
}
|
Reference in New Issue
Block a user