Skip to main content

g2o: A General Framework for Graph Optimization (Python bindings)

Project description

g2o - General Graph Optimization

Ubicoders g2opy edition

Static Badge Static Badge Static Badge Static Badge

This project is based on the original g2o maintainer as below.

This porject provide windows and linux off the shelf packge including the .dll and .so files as well as the types of the apis for intellisense.

Otherthan that, same as g2o's pymem branch

Latest Commit base:

  • 70f058fde4516505ecb3b392b25bd66b2f4fdf47 (Sep 21, 2025)

How it works

Built the .whl with the damn .dll and .so files for god xxxxing sake.

The pip packge name is pyg2o. But import with import g2opy as g2o

Intellisense Enhanced

sample1

sample2

Supported Python Versions

  • 3.10 ✅
  • 3.11 ✅
  • 3.12 ✅
  • 3.13 ✅

Supproted Numpy Version

  • numpy 1 ⬜
  • numpy 2 ✅

Tested OS and Python

  • Windows 11 ✅
  • Ubuntu 20 ⬜
  • Ubuntu 22 ⬜
  • Ubuntu 24 ✅
  • Ubuntu 25 ✅

ubuntu dependencies

sudo apt-get install -qq qtdeclarative5-dev qt5-qmake libqglviewer-dev-qt5 libsuitesparse-dev libeigen3-dev -y
pip install "numpy>=2.0"

For the new conda env

conda install -y -c conda-forge "libstdcxx-ng>=12" "libgcc-ng>=12" libgomp

Test the installaton

import numpy as np
import g2opy as g2o
np.set_printoptions(precision=3)
np.set_printoptions(suppress=True)
from collections import defaultdict

def showCameraPoses(optim, idx, N):
    for i in range(idx, idx + N):
        T = optim.vertex(i).estimate().matrix()
        trans = T[:3, 3]
        print('camera pose at ', i, ': ', trans)

def calcSSE(optim, idx, wPts):
    sse = 0
    N = wPts.shape[0]
    for i in range(idx, idx + N):
        guessedWpt = optim.vertex(i)
        error = guessedWpt.estimate() - wPts[i-idx]
        sse += np.sum(error ** 2)
    return sse

def showWpts(optim, idx, N):
    for i in range(idx, idx + N):
        T = optim.vertex(i).estimate()
        #T = np.round(T, 0)
        print('guessed wPt at ', i-idx, ': ', T)

def main():   
    optimizer = g2o.SparseOptimizer()
    solver = g2o.BlockSolverSE3(g2o.LinearSolverCSparseSE3())
    solver = g2o.OptimizationAlgorithmLevenberg(solver)
    optimizer.set_algorithm(solver)

    f, p = 200, 256
    baseline = 0.3
    K = np.array([[f, 0, p],
                  [0, f, p],
                  [0, 0, 1]])

    wPts = np.array([
        [0, 0, 10],
        [-1, 3, 30],
        [2, 2, 37.2],
    ])

    num_pose = 10
    for i in range(0, int(num_pose/2)):
        pose = g2o.Isometry3d(np.identity(3), [(i-2)*10, 0, 0])
        v_se3 = g2o.VertexSCam()
        v_se3.set_cam(f, f, p, p, baseline)
        v_se3.set_id(i)
        v_se3.set_estimate(pose)
        if i < 2:
            v_se3.set_fixed(True)
        v_se3.set_all() # sets transfrom, projection, dR (angle)
        optimizer.add_vertex(v_se3)

    for i in range(int(num_pose/2), num_pose):
        pose = g2o.Isometry3d(np.identity(3), [0, (i - int(num_pose/2)- 2) * 10, 0])
        v_se3 = g2o.VertexSCam()
        v_se3.set_cam(f, f, p, p, baseline)
        v_se3.set_id(i)
        v_se3.set_estimate(pose)
        v_se3.set_fixed(False)
        v_se3.set_all() # sets transfrom, projection, dR (angle)
        optimizer.add_vertex(v_se3)

    point_id = 0

    for i, wpt in enumerate(wPts):
        guessed_wPt = g2o.VertexPointXYZ()
        guessed_wPt.set_id(num_pose + point_id)
        guessed_wPt.set_marginalized(True)
        guessed_wPt.set_estimate(wpt + np.random.randn(3) )
        optimizer.add_vertex(guessed_wPt)

        for j in range(num_pose):
            z = optimizer.vertex(j).map_point(wpt)
            if i > 1:
                z +=  np.random.randn(3)
            edge = g2o.EdgeXyzVsc()
            edge.set_vertex(0, guessed_wPt)
            edge.set_vertex(1, optimizer.vertex(j))
            edge.set_measurement(z)
            edge.set_information(np.identity(3))
            optimizer.add_edge(edge)

        point_id += 1

    sse0 = calcSSE(optimizer, num_pose, wPts)
    print('\nRMSE (inliers only):')
    print('before optimization:', np.sqrt(sse0 / wPts.shape[0]))
    showCameraPoses(optimizer, 0, num_pose)
    showWpts(optimizer, num_pose, 3)


    print('Performing full BA:')
    optimizer.initialize_optimization()
    optimizer.set_verbose(False)
    optimizer.optimize(100)

    sse1 = calcSSE(optimizer, num_pose, wPts)

    print('\nRMSE (inliers only):')
    print('after  optimization:', np.sqrt(sse1 / wPts.shape[0]))
    showCameraPoses(optimizer, 0, num_pose)
    showWpts(optimizer, num_pose, 3)


if __name__ == '__main__':
    main()

see the orignal readme at https://github.com/RainerKuemmerle/g2o

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distributions

No source distribution files available for this release.See tutorial on generating distribution archives.

Built Distributions

If you're not sure about the file name format, learn more about wheel file names.

ubicoders_g2opy-2.1.4-cp313-cp313-win_amd64.whl (19.3 MB view details)

Uploaded CPython 3.13Windows x86-64

ubicoders_g2opy-2.1.4-cp313-cp313-manylinux_2_39_x86_64.whl (27.4 MB view details)

Uploaded CPython 3.13manylinux: glibc 2.39+ x86-64

ubicoders_g2opy-2.1.4-cp312-cp312-win_amd64.whl (19.3 MB view details)

Uploaded CPython 3.12Windows x86-64

ubicoders_g2opy-2.1.4-cp312-cp312-manylinux_2_39_x86_64.whl (27.4 MB view details)

Uploaded CPython 3.12manylinux: glibc 2.39+ x86-64

ubicoders_g2opy-2.1.4-cp311-cp311-win_amd64.whl (19.3 MB view details)

Uploaded CPython 3.11Windows x86-64

ubicoders_g2opy-2.1.4-cp311-cp311-manylinux_2_39_x86_64.whl (27.4 MB view details)

Uploaded CPython 3.11manylinux: glibc 2.39+ x86-64

ubicoders_g2opy-2.1.4-cp310-cp310-win_amd64.whl (19.3 MB view details)

Uploaded CPython 3.10Windows x86-64

ubicoders_g2opy-2.1.4-cp310-cp310-manylinux_2_39_x86_64.whl (27.4 MB view details)

Uploaded CPython 3.10manylinux: glibc 2.39+ x86-64

File details

Details for the file ubicoders_g2opy-2.1.4-cp313-cp313-win_amd64.whl.

File metadata

File hashes

Hashes for ubicoders_g2opy-2.1.4-cp313-cp313-win_amd64.whl
Algorithm Hash digest
SHA256 f2845a5b0a83d07487bea5d2124f04a44ca7be121c9217fee5f7253a83e923c0
MD5 66cfeec70175013e8ab6931041fe4e69
BLAKE2b-256 8489a3c646fa1185d714c8e1486d66dfca6123d7030753f7934391186a235e64

See more details on using hashes here.

File details

Details for the file ubicoders_g2opy-2.1.4-cp313-cp313-manylinux_2_39_x86_64.whl.

File metadata

File hashes

Hashes for ubicoders_g2opy-2.1.4-cp313-cp313-manylinux_2_39_x86_64.whl
Algorithm Hash digest
SHA256 71472fc757b0fb5b0238f88953ca73eb6901aac8760a46a0d57fb931dce700bb
MD5 c459884fcf13f02796132c762e011d87
BLAKE2b-256 d8390995bcb9c9a7b4ac0e9e9cc059814af2d3985060a0c0e8de4d7ca2b93ad0

See more details on using hashes here.

File details

Details for the file ubicoders_g2opy-2.1.4-cp312-cp312-win_amd64.whl.

File metadata

File hashes

Hashes for ubicoders_g2opy-2.1.4-cp312-cp312-win_amd64.whl
Algorithm Hash digest
SHA256 001ee3e0f308a64a90c209a7dee0fb5c4969f4c54c827780c8924cad8a1f36c5
MD5 3d4ff2b5c199c2b97a4244d7b1490c28
BLAKE2b-256 02bef038671824c47f9aaa8fe50b3dfa5e1189e42c465b8b291236ae7057a115

See more details on using hashes here.

File details

Details for the file ubicoders_g2opy-2.1.4-cp312-cp312-manylinux_2_39_x86_64.whl.

File metadata

File hashes

Hashes for ubicoders_g2opy-2.1.4-cp312-cp312-manylinux_2_39_x86_64.whl
Algorithm Hash digest
SHA256 37ebeec6e95a7a64594c6d1970a51db10007968bae7d3cb968d5ce59d5fc6d2b
MD5 cfc1e1346e90bd4d8af46faee32c951b
BLAKE2b-256 2dbdd3180e90bb132c34c9d4f9839cf85f438185c550e4bf266a4c6d8afa5e9c

See more details on using hashes here.

File details

Details for the file ubicoders_g2opy-2.1.4-cp311-cp311-win_amd64.whl.

File metadata

File hashes

Hashes for ubicoders_g2opy-2.1.4-cp311-cp311-win_amd64.whl
Algorithm Hash digest
SHA256 001c9c2d3fcdfde827b20f0e57d48141faca0267d675844f7b4766cfb096c0a2
MD5 bf03fec270ef8841332a55f260653eaf
BLAKE2b-256 223681cde90bc454b406a828d1a04234b5a1cbc1ac2343486fe82ff06188f790

See more details on using hashes here.

File details

Details for the file ubicoders_g2opy-2.1.4-cp311-cp311-manylinux_2_39_x86_64.whl.

File metadata

File hashes

Hashes for ubicoders_g2opy-2.1.4-cp311-cp311-manylinux_2_39_x86_64.whl
Algorithm Hash digest
SHA256 2ad30274a1e496169cbc57827910cce2defa9539de5288b8f92e8519662a1bee
MD5 282582b1f2eef67d92f09c133922a479
BLAKE2b-256 9fc4358c2cb8dd0854269c796a950886286d9892bf9b3c93b358d6f1b47fbbb8

See more details on using hashes here.

File details

Details for the file ubicoders_g2opy-2.1.4-cp310-cp310-win_amd64.whl.

File metadata

File hashes

Hashes for ubicoders_g2opy-2.1.4-cp310-cp310-win_amd64.whl
Algorithm Hash digest
SHA256 d99ad59cc677fc90b7d54a7ee44f5616e4dc0adc9b6b7d8132887178c5a1dbd5
MD5 b80ac7def5ea181ece7db3d5c44f98b9
BLAKE2b-256 cf8ed388543c9557792e57659830aa4f16f3156a4a2ffaea7b95d8e89035cf15

See more details on using hashes here.

File details

Details for the file ubicoders_g2opy-2.1.4-cp310-cp310-manylinux_2_39_x86_64.whl.

File metadata

File hashes

Hashes for ubicoders_g2opy-2.1.4-cp310-cp310-manylinux_2_39_x86_64.whl
Algorithm Hash digest
SHA256 243c2e7621739927717a917e5b5aa4b00ac82e0bc651cddfbfdf287e19072c21
MD5 bed659d4548aca0284bc543c6cd99ef0
BLAKE2b-256 ab400a94af7bd5cd512700853294d85391412240684668605f65e3e92fcfa293

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page