Скажем, у меня есть эта дата, например:
12-DEC-14 11.55.51.000000000 AM
и затем я назначил его переменной, скажем:
$date = '12-DEC-14 11.55.51.000000000 AM';
Теперь вопрос в том, как добавить 1 месяц или 2 месяца к этой $date
используя только php, без использования каких-либо функций даты oracle sql, просто чистую php, потому что я сохраню результат в таблице oracle db в том же формате,
Результат должен выглядеть следующим образом:
$nextmonth = '12-JAN-15 11.55.51000000000 AM';
Тогда, когда я смогу сохранить этот $nextmonth
в столбце таблицы. Так как?
Вы можете использовать классы DateTime
в этом случае, загрузить эту дату и определить ее формат. Затем, создав объект datetime, настройте его на количество х месяцев, а затем снова представьте его в исходном формате.
$input = '12-DEC-14 11.55.51.000000000 AM';
$date = DateTime::createFromFormat('d-M-y h.i.s A', $input);
$next_month = clone $date;
$next_month->modify('+1 month');
echo strtoupper($next_month->format('d-M-y h.i.s A'));
Это, вероятно, только очень длинный комментарий, а не реальный ответ, но некоторые из ваших комментариев позволяют мне думать, что у нас есть экземпляр проблемы XY:
это TIMESTAMP (6), но формат точно подобен этому внутри столбца 12-DEC-14 11.55.51.000000000 AM
как в случае следующих 9 нулей?, это не вызовет ошибок в oracle, если я просто добавлю его, например, например, echo strtoupper ($next_month-> format ('dMy his000000000 A'));
TIMESTAMP(6)
хранит информацию о дате ("момент времени"). У него нет никакого "формата". TIMESTAMP
- отличный тип данных, поскольку они позволяют вам легко выполнять вычисления на данных и времени с высокой точностью на уровне БД, например, "добавление одного месяца".
Но без явного запроса с вашей стороны формат по умолчанию используется для преобразования временных меток из и в строки.
Возможно, ваша настоящая проблема заключается в том, что Oracle пытается неявно преобразовывать вашу строку в timestamp с использованием стандартного формата. Как правило, гораздо лучше идея явно преобразовать тип данных самостоятельно. Из документации:
Oracle рекомендует указать явные преобразования, а не полагаться на неявные или автоматические преобразования, по следующим причинам:
- [...]
- неявное преобразование зависит от контекста, в котором оно происходит, и может не работать одинаково в каждом случае. Например, неявное преобразование из значения datetime в значение VARCHAR2 может возвращать неожиданный год в зависимости от значения параметра NLS_DATE_FORMAT.
Обратите внимание, что вышеприведенный оператор также относится к TIMESTAMP
, так как "стандартный" формат определяется пользователем с помощью NLS_TIMESTAMP_FORMAT
.
В документации PHP есть аналогичное предупреждение:
Столбцы DATE возвращаются в виде строк, отформатированных в текущем формате даты. Формат по умолчанию можно изменить с помощью переменных среды Oracle, таких как NLS_LANG или ранее выполненной командой ALTER SESSION SET NLS_DATE_FORMAT.
В качестве личного предложения я бы сказал, что вы никогда не должны полагаться на неявное преобразование даты и времени, так как любое изменение соответствующих параметров конфигурации на уровне DB или для текущего сеанса приведет к поломке вашего кода.
Таким образом, в зависимости от того, как вы вставляете свое значение, использование явного формата может быть таким же простым, как обертывание переменной привязки в правильном TO_TIMESTAMP(....)
:
// query the original data
$q = oci_parse ($connection ,
"INSERT INTO ....
VALUES (TO_TIMESTAMP(:date_as_str, 'YYYY-MM-DD HH:MI:SS.FF'), other_columns...)");
$q = oci_parse ($connection ,
"INSERT INTO ....
VALUES (TO_TIMESTAMP(:date_as_str, 'YYYY-MM-DD HH:MI:SS.FF'), other_columns...)");
Возвращаясь к вашему первоначальному вопросу: "Как добавить один месяц в сырую дату" "Я сохраню результат в таблице oracle db в том же формате данных формата ", это должно быть так же просто, как добавить 1 месяц при вставке значения:
$q = oci_parse ($connection ,
"INSERT INTO ....
VALUES (TO_TIMESTAMP(:date_as_str, 'YYYY-MM-DD HH:MI:SS.FF')
+ INTERVAL '1' MONTH, other_columns...)");
echo strtoupper($next_month->format('dMy his000000000 A'));