我有一个为执行ETL工作而创建的自定义python应用程序。从本质上讲,它运行良好,但是我很难找到一种优化的方法来将数据帧中的数据类型绑定到MSSQL的安全类型。
我现在正在做什么:
def _bindKnownType(self, val):
"""docstring"""
if isinstance(val, bool):
val = int(val)
elif isinstance(val, pd._libs.tslibs.timestamps.Timestamp):
val = val.strftime('%Y-%m-%dT%H:%M:%S.%f')[:-3]
elif pd.isnull(val):
val = None
return val
def InsertDf(df)
"""docstring"""
values = []
for arr in df.values:
values.append(list(arr))
safeVals = []
for iter in values:
v = [self._bindKnownType(v) for v in iter]
safeVals.append(v)
values = safeVals
mySQLInsertFunction(df, values)
因此,以上是几个功能。第一个获取值并检查其类型,如有必要,将其强制转换;第二个是中间函数,该函数将数据帧中的所有值读取到一个列表中,然后遍历该列表,将每个值传递给_bindKnownType
函数。
我上面的解决方案糟透了。非常慢我确定我可以将所有必要的转换作为矢量化函数执行,但是我很难获得对象的真实数据类型。有人对此有很好的解决方案吗?我确定我一定不是第一个为此争吵的人...
下面是使用applymap的示例:
df.applymap(lambda x: _bindKnownType(x))
这仍然很慢,要在1000行90列的数据帧上运行100次要花费将近4分钟。
我已经研究过使用df.astype()
,但这似乎并不可行,因为它利用了df中的框式类型而不是值的实际类型。