Member 11845035 Ответов: 2

Проблема вставки записи с datetime в SQL server 2014 через ODBC C++


У меня есть простой код c++ для вставки записи в SQL Server 2014 через ODBC. Он прекрасно работает с полями varchar, но не работает с полем datetime.

Может ли кто-нибудь помочь понять, что это неправильно? У меня всегда есть:

"22018:1:0:[Microsoft][драйвер ODBC SQL Server]недопустимое символьное значение для спецификации cast\n"

Если я ошибаюсь здесь с моим вопросом, пожалуйста, дайте подсказку, какой форум подходит лучше. Я потратил несколько дней, но не могу найти решение. За любую помощь буду очень признателен.

Что я уже пробовал:

SQLHSTMT hstmt;
SQLRETURN rc;

rc = SQLAllocHandle(SQL_HANDLE_STMT, dbc, &hstmt);
if(!SQL_SUCCEEDED(rc))
    return NULL;

SQLCHAR buf[64];
SQLLEN len;
SQLCHAR buf2[255];
SQLLEN len2;
SQLLEN len3;
double f;
rc = SQLBindParameter(hstmt, 1, SQL_PARAM_INPUT, SQL_C_CHAR, SQL_TYPE_TIMESTAMP, 19, 0, (SQLCHAR*)buf, 0, &len);
rc = SQLBindParameter(hstmt, 2, SQL_PARAM_INPUT, SQL_C_CHAR, SQL_VARCHAR, 255, 0, (SQLCHAR*)buf2, 0, &len2);
rc = SQLBindParameter(hstmt, 3, SQL_PARAM_INPUT, SQL_C_FLOAT, SQL_FLOAT, 15, 0, &f, 0, &len3);
rc = SQLPrepare(hstmt, (SQLCHAR*)"insert into test(timepoint,strvalue,floatvalue) values (?,?,?)", SQL_NTS);

strcpy((char*)buf,"2017-10-10T00:08:14");
len=strlen("2017-10-17T00:08:14");
strcpy((char*)buf2,"simple string");
len2=strlen("simple string");
f=1.34e+8;

SQLSMALLINT NumParams;
SQLNumParams(hstmt, &NumParams);
rc = SQLExecute(hstmt);

2 Ответов

Рейтинг:
2

debasish mishra

Invalid character value for cast specification comes from the driver when it detects a string to date time conversion.I urge you to change the data type to a string type or you can tune the logic to ensure that you don't get strings here.


Jochen Arndt

Использование строк для хранения даты и/или времени в базе данных-плохой совет. Такие типы должны всегда храниться в двоичных форматах и передаваться как таковые.

Рейтинг:
2

Jochen Arndt

Всегда передавайте временные поля с использованием двоичных данных. Это позволяет избежать проблем с преобразованием строк в такие поля.

Просто найдите соответствующий тип C для типа поля. Для SQL_TYPE_TIMESTAMP это SQL_C_TYPE_TIMESTAMP:

С идентификатором типа SQL_C_TYPE_TIMESTAMP[c]

ODBC C typedef SQL_TIMESTAMP_STRUCT

C-тип
struct tagTIMESTAMP_STRUCT {  
   SQLSMALLINT year;  
   SQLUSMALLINT month;  
   SQLUSMALLINT day;  
   SQLUSMALLINT hour;  
   SQLUSMALLINT minute;  
   SQLUSMALLINT second;  
   SQLUINTEGER fraction;[b]   
} TIMESTAMP_STRUCT;[a]

Непроверенный пример:
TIMESTAMP_STRUCT ts;
ts.year = 2017;
ts.month = 10;
ts.day = 10;
ts.hour = 8;
ts.minute = 14;
ts.second = 0;
ts.fraction = 0;
len = sizeof(ts);
rc = SQLBindParameter(hstmt, 1, SQL_PARAM_INPUT, SQL_C_TYPE_TIMESTAMP, SQL_TYPE_TIMESTAMP, 19, 0, &ts, sizeof(ts), &len);