/** @file store.htable.h * * @brief Simple in-memory triple store back end based on hash tables. * * This is the simplest choice to do in-memory manipulation of RDF graphs and * it has some limitations: most notably, it only supports triples without * context (one graph per store) and it is not indexed. This means that it is * optimized for fast writes and sequential lookups (iteration). Lookups on * arbitrary terms are supported but require iterating over all the triples. * This implementation is most convenient for graphs where retrieval is done * via iteration. * * Also, as it may be obvious, this store is not persistent. * * For faster random lookups and persistence, the MDB backend is preferred. If * persistence is not required (e.g. ingesting and manipulating a very large * graph and outputting some results on a file) an ad-hoc MDB store located in * RAM disk can be used, which is much faster. */ #ifndef _LSUP_STORE_HTABLE_H #define _LSUP_STORE_HTABLE_H #include "buffer.h" #include "store.h" typedef struct ht_store_t LSUP_HTStore; typedef struct ht_iterator_t LSUP_HTIterator; LSUP_HTStore * LSUP_htstore_new (const size_t size); /** @brief Boolean operation on hash table triples. * * The resulting store is compacted to the minimum size necessary to hold all * results. * * @param[in] op Operation type. See #LSUP_bool_op * * @param[in] s1 First store. * * @param[in] s2 Second store. * * @return New store resulting from the operation. It must be freed with * #LSUP_htstore_free after use. */ LSUP_HTStore * LSUP_htstore_bool_op ( const LSUP_bool_op op, const LSUP_HTStore *s1, const LSUP_HTStore *s2); /** @brief Free a hash table store. */ void LSUP_htstore_free (LSUP_HTStore *ht); /** @brief Duplicate a store. * * @param[in] src Store to duplicate. * * @return New store. It must be freed with #LSUP_htstore_free() after use. */ LSUP_HTStore * LSUP_htstore_copy (const LSUP_HTStore *src); /** @brief Copy contents of a store to another store. * * The destination is not initialized, so copy is cumulative with the existing * content. * * @param[in] Store to copy to. It must be already initialized via * #LSUP_htstore_new(), #LSUP_htstore_copy(), etc. * * @param[in] src Store to copy from. */ LSUP_rc LSUP_htstore_copy_contents (LSUP_HTStore *dest, const LSUP_HTStore *src); /** @brief Count triples in a store. * * @parm[in] store HTStore handle. * * @return Number of triples in the store. */ size_t LSUP_htstore_size (const LSUP_HTStore *ht); /** @brief Add a term to the store. * * @parm[in] store HTStore handle. * * @param[in] sterm Serialized term to insert. The term is copied and may be * safely freed after the operation. * * @return LSUP_OK on success; LSUP_NOACTION if the term exists already; <0 * on error. */ LSUP_rc LSUP_htstore_add_term (LSUP_HTStore *store, const LSUP_Buffer *sterm); /** @brief Initialize a loop to add triples to a store. * * @param[in] store Store handler. * * @return Iterator to be used with #LSUP_htstore_add_iter(). It must be freed * with #LSUP_htstore_add_done(). */ LSUP_HTIterator * LSUP_htstore_add_init (LSUP_HTStore *store); /** @brief Add triples to the store. * * @param[in] it Iterator handle created with #LSUP_htstore_add_init(). * * @param[in] sspo Serialized buffer triple to add. */ LSUP_rc LSUP_htstore_add_iter (LSUP_HTIterator *it, const LSUP_BufferTriple *sspo); /** @brief Free resources related to an add loop. * * @param[in] it Iterator to free. */ void LSUP_htstore_add_done (LSUP_HTIterator *it); /** @brief Find triples by pattern matching and return an iterator. * * The iterator may yield results by using #LSUP_htiter_next() and must be * freed with #LSUP_htiter_free(). * * @param[in] store Store to search in. * * @param[in] ss Serialized subject term. If NULL, the term is unbound. * * @param[in] sp Serialized predicate term. If NULL, the term is unbound. * * @param[in] so Serialized object term. If NULL, the term is unbound. * * @param[out] ct If not NULL, it is populated with the number of results. Use * only if necessary: since the hash table is not indexed, retrieving the * count requires looping over the results, thus slowing down the operation. * * @return Iterator for lookup results. */ LSUP_HTIterator * LSUP_htstore_lookup ( LSUP_HTStore *store, const LSUP_Buffer *ss, const LSUP_Buffer *sp, const LSUP_Buffer *so, size_t *ct); /** @brief Find the next triple in a lookup and return the result. * * @param[in] it Iterator obtained from #LSUP_htstore_lookup(). * * @param[out] spo Serialized triple pointer to be populated with the result, * if found. * * @return LSUP_OK if a result was found; LSUP_END if the end of the iterator * is reached. */ LSUP_rc LSUP_htiter_next (LSUP_HTIterator *it, LSUP_BufferTriple *sspo); /** @brief Count of lookup results or triples added in an iteration. * * @param[in] it Iterator handle. * * @return Number of results yielded, or triples added, at a certain point of * an iterator. */ /* size_t LSUP_htiter_count (const LSUP_HTIterator *it); */ /** @brief Free an iterator. * * @param[in] it Iterator handle obtained from #LSUP_htstore_lookup(). */ void LSUP_htiter_free (LSUP_HTIterator *it); /** @brief Remove triples by pattern matching. * * The search criteria are the same used for #LSUP_htstore_lookup(). * * @param[in] store Store to remove triples from. * * @param[in] ss Serialized subject term. If NULL, the term is unbound. * * @param[in] sp Serialized predicate term. If NULL, the term is unbound. * * @param[in] so Serialized object term. If NULL, the term is unbound. * * @param[out] Optional pointer to a counter. If not NULL, it is populated with * the number of triples removed. It is undefined if LSUP_DB_ERR is * returned. * * @return LSUP_OK if any triples were deleted; LSUP_NOACTION if no triples * were found for deletion; <0 on error. */ LSUP_rc LSUP_htstore_remove ( LSUP_HTStore *store, const LSUP_Buffer *ss, const LSUP_Buffer *sp, const LSUP_Buffer *so, size_t *ct); #endif // _LSUP_STORE_HTABLE_H