看起来每一种方法都很好地涵盖了选择某些列和按谓词过滤等基本情况,但我想知道对于更高级的情况,每种方法的比较情况如何。用一种方式表达复杂的查询比用另一种方式更容易吗?一个库是否缺少其他库所包含的任何功能?
发布于 2011-02-04 15:26:26
ClojureQL和clojure.contrib.sql是两个完全不同的库。第一个目标是实现关系代数中的原语,并将这些原语编译成SQL92。它还提供了可适用于特定于数据库SQL方言的可扩展编译器。第二个是用于从Clojure代码使用JDBC的轻量级帮助器集。
查询中
clojure.contib.sql
使用clojure.contib.sql时,您必须使用SQL来编写查询。下面是一个例子:
(sql/with-connection db
(sql/with-query-results rs ["select * from customer"]
(doseq [r rs] (println (:lastname r))))ClojureQL
由于ClojureQL主要是一种SQL语言,因此它提供了丰富的基于的来创建SQL。我将跳过高级示例,只向您展示与上述查询等效的ClojureQL:
(sql/with-connection db
(cql/with-results [rs (cql/table :customer)]
(doseq [r rs] (println (:lastname r))))您可以使用这两种方法来表达任意复杂的查询,但是contrib.sql要求您编写SQL代码。请注意,SQL相对于标准ClojureQL的主要优势是可组合性。它的table函数返回一个表示指定表上的查询的RTable对象,您可以在该对象上链接其他ClojureQL函数来创建所需的查询,然后取消对其的引用以执行该查询。有关如何创建更复杂查询的详细信息,请参阅ClojureQL examples page和documentation。
插入、更新和删除
clojure.contib.sql
clojure.contrib.sql提供了一套全面的函数来插入、更新和删除行。
记录是maps
(insert-rows table & rows),的记录,行是vectors
(insert-values table column-names & value-groups)的记录
(update-values table where-params record)(update-or-insert-values table where-params record)(delete-rows table where-params)ClojureQL
ClojureQL提供了三个RTable方法来操作指定的表数据:
conj!,它是contri.sql的insert-recordsdisj!的快捷方式,它是contri.sql的delete-rowsupdate-in!的快捷方式,类似于contri.sql的update-or-insert-values这些方法具有使用SQL谓词语法的优点,但是目前ClojureQL的这一部分不会生成数据库不可知的ClojureQL,因为它是从编译器分离出来的。我打算在不久的将来通过合并来自我写的另一个库的代码来解决这个问题。
模式操作
clojure.contib.sql
clojure.contrib.sql仅提供用于创建和删除表的create-table和drop-table。请注意,这些都是非常简单的函数,不会使您的代码可移植。要修改一个表,您需要使用do-commands函数发送SQL ALTER语句。
ClojureQL
未提供架构操作帮助器。
Lobos (无耻插头;-)
这是我写的一个库,用来填补这两个库留下的漏洞。这是一项正在进行的工作,但是您已经获得了一个Clojure DSL,它可以以一种数据库不可知的方式发送任何DDL语句。
下面是一个创建表的基本示例:
(create (table :users (integer :id :unique)))并对其进行修改:
(alter :add (table :users (text :name)))您可以通过访问website或github page获取有关该库的更多信息。它的目标是提供更高级别的功能,如迁移和声明性模式操作。
其他
clojure.contrib.sql有两个额外的低级帮助器,请参阅complete documentation
关于这些库如何处理数据库连接,还有更多要说的,但我将留待下一天再讲!
P.S.:请注意,ClojureQL和Lobos都是相对年轻的库,仍然需要一些工作。这两个项目都是从最初的ClojureQL项目发展而来的,该项目是一个涵盖整个SQL语言的领域特定语言。ClojureQL已经有了一个稳定的API,但只提供了一个与SQL92兼容的编译器。Lobos具有多个数据库的编译器支持。但仍在积极开发中,其API仍可更改。
更新:在刘的建议之后,我做了一些修改。ClojureQL本身并不打算与数据库无关,而是为用户提供了用特定于数据库的编译器替换编译器的方法。请注意,SQL的DML部分比DDL部分标准化得多。
https://stackoverflow.com/questions/4894161
复制相似问题