GithubHelp home page GithubHelp logo

jamesgallicchio / leancolls Goto Github PK

View Code? Open in Web Editor NEW
30.0 4.0 7.0 3.07 MB

WIP collections library for Lean 4

Home Page: https://jamesgallicchio.github.io/LeanColls/docs/

License: Apache License 2.0

Lean 100.00%
lean4

leancolls's Introduction

Lean Collections Library

General-purpose collections library implemented in pure Lean 4.

Collection interfaces and utilities have grown independently in many Lean projects. This library is an attempt to unify and extend those interfaces/utilities.

Includes:

  • Consistent interfaces for collections, to abstract from an implementation
  • Thorough body of lemmas for all collections (via the consistent interfaces)
  • Utilities to write clean (i.e. proof-friendly) code, without sacrificing performance

Usage

Add the following to your lakefile.lean:

require leancolls from git
  "https://github.com/JamesGallicchio/LeanColls" @ "main"

Branches & Releases

  • branch main: stays on latest stable version of the compiler, which also pins us to the corresponding stable mathlib release.
  • branch mathlib-nightly: automatically updated every night for anyone who needs a more up to date mathlib/compiler.
  • tag v4.*.0: the first commit which compiles on v4.*.0

Please open an issue if none of these cover your particular use case!

Docs

The latest documentation is available here.

Design

See notes.md for design philosophy and inspiration sources.

Contributing

Issues and PRs are welcome. You can also DM me on the Lean community Zulip as James Gallicchio.

Shoutout to @lecopivo and @T-Brick for helping to maintain and expand the library in its early stages :-)

leancolls's People

Contributors

digama0 avatar jamesgallicchio avatar lecopivo avatar t-brick avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar

leancolls's Issues

Index notation cause internal exception

This code

import LeanColls.Classes.Indexed

open LeanColls

variable {Cont Idx Elem} [IndexType Idx] [Indexed Cont Idx Elem] [Inhabited Elem]

example (f : Idx → Elem) :
  Function.invFun (fun (f : Idx → Elem) => Indexed.ofFn (C:=Cont) f)
  =
  fun x i => x[i] := sorry

cause

internal exception: isDefEqStuck

I will investigate this as it is my doing.

Map operation class

Functor only applies to type constructors (Type u -> Type v). So, is insufficient for a general purpose map : (A -> B) -> CA -> CB where perhaps CA and CB cannot contain arbitrary element types.

Example: Functor ByteArray does not typecheck, even though we can give map : (Byte -> Byte) -> ByteArray -> ByteArray

Suggested implementation:

class Map (C : Type w) (τ : Type x) (C' : Type y) (τ' : Type z) where
  map : (f : τ → τ') → C → C'

This conflicts with the current Map class (which is the bag of associations abstraction commonly called a Map in other languages).

We could

  1. Name the new class MapOp? Since we will export MapOp (map) it will still be visible, but with the current naming scheme, theorems about map will end up in the MapOp.theorems_about_map namespace.
  2. Rename current Map to MapBag or similar. I don't .. hate this solution? because it emphasizes the class's relationship to Bag, but this goes against other languages with interfaces named Map.

`Index.card` has an extra universe parameter

As in title.

set_option pp.universes true
#check IndexType.card (Prod (Fin 2) (Fin 2))
-- IndexType.card.{0, u_1} (Prod.{0, 0} (Fin 2) (Fin 2))

Probably we should not require Fold in the definition of IndexType, instead just expecting the universe to be Fold at any functions that need it.

`reduce` and family

Add reduce? : C -> (t -> t) -> Option t with default implementation for any Foldable collection

Dependently typed `Indexed`

In SciLean, I need an unified interface to deal with functions, arrays(fixed sized) and structs. This can be done with a variant of Indexed which has dependent types. I call it StructType

I'm really not sure if there should be separate dependently typed version of Indexed or not. On one hand, dealing with dependent types is annoying and most of the time not necessary. On the other hand, having variant of Indexed just duplicates code.

A crucial difference of StructType from Indexed is that the index type is not marked outParam. This allows you to index for example the type Nat × ArrayN Nat n with Unit ⊕ Unit or Unit ⊕ Fin n. In SciLean, this is a crucial feature when doing automatic differentiation.

`Seq` on `List` is simp

Currently the instance : Seq (List τ) τ is marked @[simp]. The reasoning is that List is the model, so theorems should be stated in terms of List directly.

Unclear what the consequences of this decision are. I think it mostly comes down to whether you prefer 1 or 2:

1:  size c = size (toList c)
2:  size c = (toList c).length

Either way this style/simpNF decision should be documented.

Elab issues with index notation

I broke the element access notation again

variable {Cont Idx Elem} [IndexType Idx] [Indexed Cont Idx Elem]

variable (x y : Cont)

-- broken
#check Function.HasUncurry.uncurry fun i => x[i]
#check Function.HasUncurry.uncurry fun i j => (x[i],y[j])

-- works
#check Function.HasUncurry.uncurry fun i => (x[i] : Elem)
#check Function.HasUncurry.uncurry fun i j => ((x[i] : Elem),(y[j] : Elem))

Because the x[i] elaboration is postponed until the type of x[i] is known it causes failure to synthesize the instance in HasUncurry.

I'm thinking of going back to using GetElem.getElem instead of Indexed.get. Then the custom element access notation can be implemented just as a macro and the elaboration mess can be completely avoided.

Naming arguments of Ops

I would prefer if arguments of functions have (somewhat)meaningful names rather than being anonymous.

For example Fold would be defined as

class Fold (C : Type u) (τ : outParam (Type v)) where
  fold {β : Type w} (c : C) (f : β → τ → β) (init : β) : β
  foldM {β : Type w} {m : Type w → Type w} [Monad m]
      (c : C) (f : β → τ → m β) (init : β) : m β

Maybe even better would be following GetElem convention

class Fold (cont : Type u) (Elem : outParam (Type v)) where
  fold {β : Type w} (cont : Cont) (f : β → Elem → β) (init : β) : β
  foldM {β : Type w} {m : Type w → Type w} [Monad m]
      (cont : Cont) (f : β → Elem → m β) (init : β) : m β

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.