예제 #1
0
static void
test_patch_pointn_laz_compression()
{
	// 00 endian (big)
	// 00000000 pcid
	// 00000000 compression
	// 00000003 npoints
	// 0000000800000003000000050006 pt1 (XYZi)
	// 0000000200000003000000040008 pt2 (XYZi)
	// 0000000200000003000000040009 pt3 (XYZi)

	char *hexbuf = "00000000000000000000000003000000080000000300000005000600000002000000030000000400080000000200000003000000040009";
	size_t hexsize = strlen(hexbuf);
	uint8_t *wkb = bytes_from_hexbytes(hexbuf, hexsize);
	char *str;

	PCPATCH *pa = pc_patch_from_wkb(simpleschema, wkb, hexsize/2);
	PCPOINTLIST *li = pc_pointlist_from_patch(pa);

	PCPATCH_LAZPERF* paz = pc_patch_lazperf_from_pointlist(li);
	PCPOINT *pt = pc_patch_pointn((PCPATCH*) paz, 2);
	CU_ASSERT(pt != NULL);
	str = pc_point_to_string(pt);
	CU_ASSERT_STRING_EQUAL(str, "{\"pcid\":0,\"pt\":[0.02,0.03,0.04,8]}");
	pc_patch_free((PCPATCH *)paz);
	pc_point_free(pt);
	pcfree(str);

	pcfree(wkb);
	pc_patch_free(pa);
	pc_pointlist_free(li);
}
예제 #2
0
static void
test_sort_patch_is_sorted_no_compression()
{
	// 00 endian (big)
	// 00000000 pcid
	// 00000000 compression
	// 00000002 npoints
	// 0000000800000003000000050006 pt1 (XYZi)
	// 0000000200000003000000040008 pt2 (XYZi)
	// 0000000200000003000000040009 pt3 (XYZi)

	// init data
	PCPATCH *pasort;
	char *hexbuf = "00000000000000000000000003000000080000000300000005000600000002000000030000000400080000000200000003000000040009";
	size_t hexsize = strlen(hexbuf);
	uint8_t *wkb = bytes_from_hexbytes(hexbuf, hexsize);
	PCPATCH *pa = pc_patch_from_wkb(schema, wkb, hexsize/2);
	PCPOINTLIST *li = pc_pointlist_from_patch(pa);
	const char *X[] = {"X"};

	CU_ASSERT_EQUAL(pc_patch_is_sorted(pa, X, 1, PC_FALSE), PC_FALSE);
	CU_ASSERT_EQUAL(pc_patch_is_sorted(pa, X, 1, PC_TRUE), PC_FALSE);

	pasort = pc_patch_sort(pa, X, 1);
	CU_ASSERT_EQUAL(pc_patch_is_sorted(pasort, X, 1, PC_FALSE), PC_FALSE);
	CU_ASSERT_EQUAL(pc_patch_is_sorted(pasort, X, 1, PC_TRUE), PC_TRUE);

	// free
	pcfree(wkb);
	pc_patch_free(pa);
	pc_patch_free(pasort);
	pc_pointlist_free(li);
}
예제 #3
0
static void
test_patch_pointn_ght_compression()
{
	// 00 endian (big)
	// 00000000 pcid
	// 00000000 compression
	// 00000003 npoints
	// 0000000800000003000000050006 pt1 (XYZi)
	// 0000000200000003000000040008 pt2 (XYZi)
	// 0000000200000003000000040009 pt3 (XYZi)

	char *hexbuf = "00000000000000000000000003000000080000000300000005000600000002000000030000000400080000000200000003000000040009";
	size_t hexsize = strlen(hexbuf);
	uint8_t *wkb = bytes_from_hexbytes(hexbuf, hexsize);

	PCPATCH *pa = pc_patch_from_wkb(simpleschema, wkb, hexsize/2);
	PCPOINTLIST *li = pc_pointlist_from_patch(pa);

#ifdef HAVE_LIBGHT
	PCPATCH_GHT* pag = pc_patch_ght_from_pointlist(li);
	PCPOINT *pt = pc_patch_pointn((PCPATCH*) pag, 2);
	CU_ASSERT(pt != NULL);
	CU_ASSERT_STRING_EQUAL(pc_point_to_string(pt), "{\"pcid\":0,\"pt\":[0.02,0.03,0.04,8]}");
	pc_patch_free( (PCPATCH*) pag );
	pc_point_free(pt);
#endif

	// free
	pcfree(wkb);
	pc_patch_free(pa);
	pc_pointlist_free(li);
}
예제 #4
0
static void
test_sort_simple()
{
	// 00 endian (big)
	// 00000000 pcid
	// 00000000 compression
	// 00000002 npoints
	// 0000000800000003000000050006 pt1 (XYZi)
	// 0000000200000001000000040008 pt2 (XYZi)

	// init data
	PCPOINTLIST *lisort;
	PCPATCH *pasort;
	double d1;
	double d2;
	char *hexbuf = "0000000000000000000000000200000008000000030000000500060000000200000001000000040008";
	size_t hexsize = strlen(hexbuf);

	uint8_t *wkb = bytes_from_hexbytes(hexbuf, hexsize);
	PCPATCH *pa = pc_patch_from_wkb(schema, wkb, hexsize/2);
	PCPOINTLIST *li = pc_pointlist_from_patch(pa);
	const char *X[] = {"X"};

	// check that initial data are not sorted
	pc_point_get_double_by_name(pc_pointlist_get_point(li, 0), "X", &d1);
	pc_point_get_double_by_name(pc_pointlist_get_point(li, 1), "X", &d2);

	CU_ASSERT_DOUBLE_EQUAL(d1, 0.08, precision);
	CU_ASSERT_DOUBLE_EQUAL(d2, 0.02, precision);

	// sort on X attribute and check if data are well sorted
	pasort = pc_patch_sort(pa, X, 1);
	lisort = pc_pointlist_from_patch(pasort);

	pc_point_get_double_by_name(pc_pointlist_get_point(lisort, 0), "X", &d1);
	pc_point_get_double_by_name(pc_pointlist_get_point(lisort, 1), "X", &d2);

	CU_ASSERT_DOUBLE_EQUAL(d1, 0.02, precision);
	CU_ASSERT_DOUBLE_EQUAL(d2, 0.08, precision);

	// free
	pc_pointlist_free(li);
	pc_pointlist_free(lisort);
	pc_patch_free(pa);
	pc_patch_free(pasort);
	pcfree(wkb);
}
예제 #5
0
static void
test_sort_consistency()
{
	// 00 endian (big)
	// 00000000 pcid
	// 00000000 compression
	// 00000002 npoints
	// 0000000800000003000000050006 pt1 (XYZi)
	// 0000000200000001000000040008 pt2 (XYZi)

	// init data
	PCPATCH *pasort;
	char *pastr, *pasortstr;
	uint8_t *wkbsort;
	char *hexbuf = "0000000000000000000000000200000008000000030000000500060000000200000001000000040008";
	size_t hexsize = strlen(hexbuf);
	uint8_t *wkb = bytes_from_hexbytes(hexbuf, hexsize);
	PCPATCH *pa = pc_patch_from_wkb(schema, wkb, hexsize/2);
	PCPOINTLIST *li = pc_pointlist_from_patch(pa);
	const char *X[] = {"X"};

	// sort on X attribute
	pasort = pc_patch_sort(pa, X, 1);

	//chek consistency
	wkbsort = pc_patch_to_wkb(pasort, &hexsize);
	CU_ASSERT_EQUAL(wkb_get_pcid(wkb), wkb_get_pcid(wkbsort));
	CU_ASSERT_EQUAL(wkb_get_npoints(wkb), wkb_get_npoints(wkbsort));
	CU_ASSERT_EQUAL(wkb_get_compression(wkb), wkb_get_compression(wkbsort));

	pastr = pc_patch_to_string(pa);
	CU_ASSERT_STRING_EQUAL(pastr, "{\"pcid\":0,\"pts\":[[0.08,0.03,0.05,6],[0.02,0.01,0.04,8]]}");

	pasortstr = pc_patch_to_string(pasort);
	CU_ASSERT_STRING_EQUAL(pasortstr, "{\"pcid\":0,\"pts\":[[0.02,0.01,0.04,8],[0.08,0.03,0.05,6]]}");

	// free
	pcfree(wkb);
	pcfree(wkbsort);
	pcfree(pastr);
	pcfree(pasortstr);
	pc_patch_free(pasort);
	pc_patch_free(pa);
	pc_pointlist_free(li);
}
예제 #6
0
static void
test_patch_hex_in()
{
	// 00 endian (big)
	// 00000000 pcid
	// 00000000 compression
	// 00000002 npoints
	// 0000000200000003000000050006 pt1 (XYZi)
	// 0000000200000003000000050008 pt2 (XYZi)
	char *hexbuf = "0000000000000000000000000200000002000000030000000500060000000200000003000000050008";

	double d;
	char *str;
	size_t hexsize = strlen(hexbuf);
	uint8_t *wkb = bytes_from_hexbytes(hexbuf, hexsize);
	PCPATCH *pa = pc_patch_from_wkb(simpleschema, wkb, hexsize/2);
	PCPOINTLIST *pl = pc_pointlist_from_patch(pa);

	pc_point_get_double_by_name(pc_pointlist_get_point(pl, 0), "X", &d);
	CU_ASSERT_DOUBLE_EQUAL(d, 0.02, 0.000001);
	pc_point_get_double_by_name(pc_pointlist_get_point(pl, 1), "Intensity", &d);
	CU_ASSERT_DOUBLE_EQUAL(d, 8, 0.000001);

	pc_point_get_double_by_name(&(pa->stats->min), "Intensity", &d);
	CU_ASSERT_DOUBLE_EQUAL(d, 6, 0.000001);
	pc_point_get_double_by_name(&(pa->stats->max), "Intensity", &d);
	CU_ASSERT_DOUBLE_EQUAL(d, 8, 0.000001);
	pc_point_get_double_by_name(&(pa->stats->avg), "Intensity", &d);
	CU_ASSERT_DOUBLE_EQUAL(d, 7, 0.000001);

	str = pc_patch_to_string(pa);
	CU_ASSERT_STRING_EQUAL(str, "{\"pcid\":0,\"pts\":[[0.02,0.03,0.05,6],[0.02,0.03,0.05,8]]}");
	// printf("\n%s\n",str);
	pcfree(str);

	pc_pointlist_free(pl);
	pc_patch_free(pa);
	pcfree(wkb);
}
예제 #7
0
static void
test_sort_stable()
{
	// 00 endian (big)
	// 00000000 pcid
	// 00000000 compression
	// 00000002 npoints
	// 0000000800000003000000050006 pt1 (XYZi)
	// 0000000200000003000000040008 pt2 (XYZi)
	// 0000000200000003000000040009 pt3 (XYZi)

	// init data
	PCPATCH *pasort;
	char *hexbuf = "00000000000000000000000003000000080000000300000005000600000002000000030000000400080000000200000003000000040009";
	size_t hexsize = strlen(hexbuf);
	uint8_t *wkb = bytes_from_hexbytes(hexbuf, hexsize);
	PCPATCH *pa = pc_patch_from_wkb(schema, wkb, hexsize/2);
	PCPOINTLIST *li = pc_pointlist_from_patch(pa);
	const char *dims[] = {"Y"};

	// sort on Y attribute
	pasort = pc_patch_sort(pa, dims, 1);

	// check that sort is stable
	char *pastr = pc_patch_to_string(pa);
	char *pasortstr = pc_patch_to_string(pasort);
	CU_ASSERT_STRING_EQUAL(pastr, pasortstr);

	// free
	free(pastr);
	free(pasortstr);
	pcfree(wkb);
	pc_patch_free(pa);
	pc_patch_free(pasort);
	pc_pointlist_free(li);
}
예제 #8
0
Datum pcpatch_unnest(PG_FUNCTION_ARGS)
{
	typedef struct
	{
		int nextelem;
		int numelems;
		PCPOINTLIST *pointlist;
	} pcpatch_unnest_fctx;

	FuncCallContext *funcctx;
	pcpatch_unnest_fctx *fctx;
	MemoryContext oldcontext;

	/* stuff done only on the first call of the function */
	if (SRF_IS_FIRSTCALL())
	{		
		PCPATCH *patch;
		SERIALIZED_PATCH *serpatch;
		
		/* create a function context for cross-call persistence */
		funcctx = SRF_FIRSTCALL_INIT();

		/*
		* switch to memory context appropriate for multiple function calls
		*/
		oldcontext = MemoryContextSwitchTo(funcctx->multi_call_memory_ctx);

		/*
		* Get the patch value and detoast if needed.  We can't do this
		* earlier because if we have to detoast, we want the detoasted copy
		* to be in multi_call_memory_ctx, so it will go away when we're done
		* and not before.      (If no detoast happens, we assume the originally
		* passed array will stick around till then.)
		*/
		serpatch = PG_GETARG_SERPATCH_P(0);
		patch = pc_patch_deserialize(serpatch, pc_schema_from_pcid_uncached(serpatch->pcid));

		/* allocate memory for user context */
		fctx = (pcpatch_unnest_fctx *) palloc(sizeof(pcpatch_unnest_fctx));

		/* initialize state */
		fctx->nextelem = 0;
		fctx->numelems = patch->npoints;
		fctx->pointlist = pc_pointlist_from_patch(patch);

		/* save user context, switch back to function context */
		funcctx->user_fctx = fctx;
		MemoryContextSwitchTo(oldcontext);
	}

	/* stuff done on every call of the function */
	funcctx = SRF_PERCALL_SETUP();
	fctx = funcctx->user_fctx;

	if (fctx->nextelem < fctx->numelems)
	{
		Datum elem;
		PCPOINT *pt = pc_pointlist_get_point(fctx->pointlist, fctx->nextelem);
		SERIALIZED_POINT *serpt = pc_point_serialize(pt);
		fctx->nextelem++;
		elem = PointerGetDatum(serpt);
		SRF_RETURN_NEXT(funcctx, elem);
	}
	else
	{
		/* do when there is no more left */
		SRF_RETURN_DONE(funcctx);
	}
}