Pattern matchings for Go.

Go pattern matching

Mentioned in Awesome Go Go Report Card Build Status codecov GoDoc LICENSE

It's just another implementation of pattern matching in Go. I have been inspired by Python pattern matching, that's why I wanted to try writing something similar in Go :) For now the following matching are implemented :

  • Simple types (like int, int64, float, float64, bool..).
  • Struct type.
  • Slices (with HEAD, TAIL, OneOf patterns).
  • Dictionary (with ANY, OneOf pattern).
  • Regexp.
  • Additional custom matching (ability to add special matching for some, structs for example).

Usages

Fibonacci example:

func fib(n int) int {
	_, res := match.Match(n).
		When(1, 1).
		When(2, 1).
		When(match.ANY, func() int { return fib(n-1) + fib(n-2) }).
		Result()

	return res.(int)
}

Simple types:

isMatched, mr := match.Match(42).
                When(42, 10).
                Result()
// isMatched - true, mr - 10

With Structs:

  • Simple check value by type
val := TestStruct{1}

isMatched, _ := Match(val).
    When(func(TestStruct) {},  1).
    Result()
  • Check value by type and condition
val := TestStruct{1}

isMatched, _ := Match(val).
	When(func(ts TestStruct) bool { return ts.value == 42 }, 1).
	When(func(ts AnotherStruct) bool { return ts.stringValue == "hello" }, 2).
	Result()

With Maps:

isMatched, mr := match.Match(map[string]int{
                	"rsc": 3711,
                	"r":   2138,
                	"gri": 1908,
                	"adg": 912,
                }).
        	    When(map[string]interface{}{
                	"rsc": 3711,
                	"r":   2138,
                	"gri": 1908,
                	"adg": match.ANY,
            	}, true).
            	Result()

With Slices:

isMatched, mr := match.Match([]int{1, 2, 3, 4, 5, 6}).
            	When([]interface{}{match.HEAD, 3, match.OneOf(3, 4), 5, 6}, 125).
            	Result()

With regexps:

isMatched, mr := match.Match("gophergopher").
            	When("gophergopher", func() interface{} { return true }).
            	Result()

Without result:

func main() {
	Match(val).
	When(42, func() { fmt.Println("You found the answer to life, universe and everything!") }).
	When(ANY, func() { fmt.Println("No.. It's not an answer.") }).
	Result()
}

Installation

Just go get this repository in the following way:

go get github.com/alexpantyukhin/go-pattern-match

Full example

package main

import (
    "fmt"
    "github.com/alexpantyukhin/go-pattern-match"
)

func main() {
    isMatched, mr := match.Match([]int{1, 2, 3}).
        When(42, false).
        When([]interface{}{match.HEAD, 2, 3}, true).
        Result()


    if isMatched {
        fmt.Println(mr)
    }
}
Similar Resources

An efficient and feature complete Hystrix like Go implementation of the circuit breaker pattern.

An efficient and feature complete Hystrix like Go implementation of the circuit breaker pattern.

Circuit Circuit is an efficient and feature complete Hystrix like Go implementation of the circuit breaker pattern. Learn more about the problems Hyst

Dec 28, 2022

Create a cool glass-like pattern using Voronoi cells

Create a cool glass-like pattern using Voronoi cells

voronoi-glass Have you ever looked through a shower door made of intentionally uneven glass? Everything looks distorted, but maybe also beautiful. Now

Jul 21, 2022

Create production ready microservices mono repo pattern wired with Neo4j. Microservices for other languages and front end repos to be added as well in future.

Create production ready microservices mono repo pattern wired with Neo4j. Microservices for other languages and front end repos to be added as well in future.

Create Microservices MonoRepo in GO/Python Create a new production-ready project with backend (Golang), (Python) by running one CLI command. Focus on

Oct 26, 2022

An extension for discordgo to create a Discord bot quickly using the Builder pattern.

botbuilder An extension for discordgo to create a Discord bot quickly using the Builder pattern. Example usage: package main import ( "log" "os"

Oct 12, 2022

Go microservices with REST, and gRPC using BFF pattern.

Go microservices with REST, and gRPC using BFF pattern.

Go microservices with REST, and gRPC using BFF pattern. This repository contains backend services. Everything is dockerized and ready to

Jan 4, 2023

gobreaker implements the Circuit Breaker pattern in Go.

gobreaker gobreaker implements the Circuit Breaker pattern in Go.

Jan 7, 2023

Example go clean architecture folder pattern

Golang Clean Architecture (Maintenance) Berikut ini adalah folder structure pattern yang biasa saya gunakan, walaupun tidak semua nya saya terapkan di

Dec 21, 2022

File Processor in Concurrency Pattern using Golang goroutine.

 File Processor in Concurrency Pattern using Golang goroutine.

File Processor in Concurrency Pattern Implement a file processor solution in concurrency pattern using Golang goroutine. Get Started Run docker-compos

Sep 16, 2022

gRelay is an open source project written in Go that provides the circuit break pattern with a relay idea behind.

gRelay is an open source project written in Go that provides the circuit break pattern with a relay idea behind.

gRELAY gRelay is an open source project written in Go that provides: Circuit Break ✔️ Circuit Break + Relay ✔️ Concurrecny Safe ✔️ Getting start Insta

Sep 30, 2022

A Go library to iterate over potentially nested map keys using the visitor pattern

A Go library to iterate over potentially nested map keys using the visitor pattern

Mar 15, 2022

Print lines matching a pattern in repositories using GitHub API

Print lines matching a pattern in repositories using GitHub API

gh-grep Print lines matching a pattern in repositories using GitHub API Usage $ gh grep func.*schema.Schema --include=**/*.go --owner k1LoW --repo tbl

Dec 1, 2022

A convenient library to do a must pattern

must A convenient library to do a must pattern Problems Before Go 1.18, if you want to panic when the regular expression cannot compile, you need to d

Nov 15, 2022

The Operator Pattern, in Nomad

Nomad Operator Example Repostiory to go along with my The Operator Pattern in Nomad blog post. Usage If you have tmux installed, you can run start.sh

May 12, 2022

A go library that facilitates the implementation of decorator pattern.

go-decorator go-decorator is a library that facilitates the implementation of decorator pattern. Installation To install go-decorator, use go get: go

Nov 25, 2021

The Humboldt Web Framework and Toolkit. Using this as an interpeter and server, build webistes in an MVC pattern using Lua.

Humboldt Web Framework Humboldt is a framework written in Go using Lua files to build web applications. What is this framework for? People who want to

Jan 21, 2022

Collatz Conjecture Pattern for golang

collatz-conjecture-pattern- Collatz Conjecture Pattern Execution Time parthiban@C02DP2C8ML85  ~/mygit/collatz-conjecture-pattern   main ●  go run

Jan 5, 2022

A demonstration of the transactional outbox messaging pattern (+ Log Trailing) with Amazon DynamoDB (+ Streams) written in Go.

A demonstration of the transactional outbox messaging pattern (+ Log Trailing) with Amazon DynamoDB (+ Streams) written in Go.

Transactional Outbox Pattern in Amazon DynamoDB A demonstration of the transactional outbox messaging pattern (+ Log Trailing) with Amazon DynamoDB (+

Apr 12, 2022

The MapReduce pattern with Goroutines and channels to count n-grams in a directory of text files

MapReduce Ngram This Golang program implements the MapReduce pattern with Goroutines and channels to count n-grams in a directory of text files. Usage

Dec 16, 2021

A demonstration of the transactional outbox messaging pattern (+ Log Trailing) with Amazon DynamoDB (+ Streams) written in Go

🎇 Gluon A composable message bus for Event-Driven systems written in Go.

Apr 12, 2022
Comments
  • Unable to match `OneOf` with `slice`

    Unable to match `OneOf` with `slice`

    Hi!

    Using OneOf with slice does not work:

    func TestMatch(t *testing.T) {
    	isMatched, _ := Match([]string{"one", "two", "three"}).
    		When(OneOf([]string{"one", "two", "three"}), true).
    		Result()
    
    	assert.True(t, isMatched)
    }
    

    Do you have any idea on what is the fix for this? My task involve matching a slice of string with some pattern groups, in which Match is a perfect match. For a workaround, I can try writing a wrapper like:

    func OneOfWrapper(items ...interface{}) boolean {
    	isMatched, _ := ...
    	return isMatched || OneOfWrapper(items[1:]...)
    }
    

    But it is not a preferable way, I suppose.

    Thanks for the awesome library!

  • Syntax Error: Unexpected newline in match.go:183:85

    Syntax Error: Unexpected newline in match.go:183:85

    Hey! Loving this library, I come from the Elixir/Elm world and wanted to give Go a try but missed my pattern matching.

    Getting a strange error when trying to compile an example from the README.

    $ belm go run belm.go
    # github.com/alexpantyukhin/go-pattern-match
    ../../go/pkg/mod/github.com/alexpantyukhin/[email protected]/match.go:183:85: syntax error: unexpected newline, expecting { after if clause
    

    Go version

    go version go1.19.1 darwin/amd64
    

    The opening brace is there, just on a newline. I managed to fix it by moving the opening brace to the same line of the if statement. So not sure if this a problem with the version of Go I'm using? But it seems very odd there would be a change to the compiler that wouldn't allow a newline after an if statement.

Leader-follower-pattern - Build leader-follower system pattern with etcd election

主备系统模式 原理 使用分布式锁实现主备节点系统。通过对分布式锁进行续期,保持长期锁, 从而使当前服务节点处于主服务节点 无法获取分布式锁的服务节点,则作为备选

Jan 24, 2022
Multi-String Pattern Matching Algorithm Using TrieHashNode

Multi-String Pattern Matching algorithm. This implementation is inspired from Aho-Corasick algorithm Getting Started modelA = mspm.NewModel("mspm_mode

Dec 9, 2022
A library that implements the outboxer pattern in go

Outboxer Outboxer is a go library that implements the outbox pattern. Getting Started Outboxer was designed to simplify the tough work of orchestratin

Dec 16, 2022
Go implementation of Fowler's Money pattern
Go implementation of Fowler's Money pattern

Money GoMoney provides ability to work with monetary value using a currency's smallest unit. This package provides basic and precise Money operations

Jan 3, 2023
🚦 Semaphore pattern implementation with timeout of lock/unlock operations.
🚦 Semaphore pattern implementation with timeout of lock/unlock operations.

?? semaphore Semaphore pattern implementation with timeout of lock/unlock operations. ?? Idea The semaphore provides API to control access to a shared

Dec 7, 2022
The implementation of the pattern observer

Event This is package implements pattern-observer Fast example import ( "github.com/agoalofalife/event" ) func main() { // create struct e := even

Dec 4, 2022
:incoming_envelope: A fast Message/Event Hub using publish/subscribe pattern with support for topics like* rabbitMQ exchanges for Go applications

Hub ?? A fast enough Event Hub for go applications using publish/subscribe with support patterns on topics like rabbitMQ exchanges. Table of Contents

Dec 17, 2022
skipmap is a high-performance concurrent sorted map based on skip list. Up to 3x ~ 10x faster than sync.Map in the typical pattern.
skipmap is a high-performance concurrent sorted map based on skip list. Up to 3x ~ 10x faster than sync.Map in the typical pattern.

Introduction skipmap is a high-performance concurrent map based on skip list. In typical pattern(one million operations, 90%LOAD 9%STORE 1%DELETE), th

Jan 8, 2023
A pluggable backend API that enforces the Event Sourcing Pattern for persisting & broadcasting application state changes
A pluggable backend API that enforces the Event Sourcing Pattern for persisting & broadcasting application state changes

A pluggable "Application State Gateway" that enforces the Event Sourcing Pattern for securely persisting & broadcasting application state ch

Nov 1, 2022
A pluggable backend API that enforces the Event Sourcing Pattern for persisting & broadcasting application state changes
A pluggable backend API that enforces the Event Sourcing Pattern for persisting & broadcasting application state changes

A pluggable "Application State Gateway" that enforces the Event Sourcing Pattern for securely persisting & broadcasting application state changes

Nov 1, 2022