Skip to content

Commit 62eb5d6

Browse files
authored
Add strings_to_ctypes_array to convert a sequence of strings into a ctypes array (#3137)
1 parent 754a52f commit 62eb5d6

File tree

2 files changed

+31
-9
lines changed

2 files changed

+31
-9
lines changed

pygmt/clib/conversion.py

+26
Original file line numberDiff line numberDiff line change
@@ -296,6 +296,32 @@ def sequence_to_ctypes_array(sequence: Sequence, ctype, size: int) -> ctp.Array
296296
return (ctype * size)(*sequence)
297297

298298

299+
def strings_to_ctypes_array(strings: Sequence[str]) -> ctp.Array:
300+
"""
301+
Convert a sequence (e.g., a list) of strings into a ctypes array.
302+
303+
Parameters
304+
----------
305+
strings
306+
A sequence of strings.
307+
308+
Returns
309+
-------
310+
ctypes_array
311+
A ctypes array of strings.
312+
313+
Examples
314+
--------
315+
>>> strings = ["first", "second", "third"]
316+
>>> ctypes_array = strings_to_ctypes_array(strings)
317+
>>> type(ctypes_array)
318+
<class 'pygmt.clib.conversion.c_char_p_Array_3'>
319+
>>> [s.decode() for s in ctypes_array]
320+
['first', 'second', 'third']
321+
"""
322+
return (ctp.c_char_p * len(strings))(*[s.encode() for s in strings])
323+
324+
299325
def array_to_datetime(array):
300326
"""
301327
Convert a 1-D datetime array from various types into numpy.datetime64.

pygmt/clib/session.py

+5-9
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@
2020
as_c_contiguous,
2121
dataarray_to_matrix,
2222
sequence_to_ctypes_array,
23+
strings_to_ctypes_array,
2324
vectors_to_arrays,
2425
)
2526
from pygmt.clib.loading import load_libgmt
@@ -897,13 +898,9 @@ def put_vector(self, dataset, column, vector):
897898

898899
gmt_type = self._check_dtype_and_dim(vector, ndim=1)
899900
if gmt_type in (self["GMT_TEXT"], self["GMT_DATETIME"]):
900-
vector_pointer = (ctp.c_char_p * len(vector))()
901901
if gmt_type == self["GMT_DATETIME"]:
902-
vector_pointer[:] = np.char.encode(
903-
np.datetime_as_string(array_to_datetime(vector))
904-
)
905-
else:
906-
vector_pointer[:] = np.char.encode(vector)
902+
vector = np.datetime_as_string(array_to_datetime(vector))
903+
vector_pointer = strings_to_ctypes_array(vector)
907904
else:
908905
vector_pointer = vector.ctypes.data_as(ctp.c_void_p)
909906
status = c_put_vector(
@@ -960,13 +957,12 @@ def put_strings(self, dataset, family, strings):
960957
restype=ctp.c_int,
961958
)
962959

963-
strings_pointer = (ctp.c_char_p * len(strings))()
964-
strings_pointer[:] = np.char.encode(strings)
965-
966960
family_int = self._parse_constant(
967961
family, valid=FAMILIES, valid_modifiers=METHODS
968962
)
969963

964+
strings_pointer = strings_to_ctypes_array(strings)
965+
970966
status = c_put_strings(
971967
self.session_pointer, family_int, dataset, strings_pointer
972968
)

0 commit comments

Comments
 (0)