1

PHP v 5.6.2

I need to convert dates such as 18-Jul-46 to give me 18/07/1946 and no amount of DateTime functions work correctly. (As strtotime wont work for dates before 1970). They all end up giving 18/07/2046 which is incorrect.

Codes I tried so far:

$date = new DateTime("18-Jul-46");
$date->format('d/m/Y');

Another one with DateTime

$date = DateTime::createFromFormat('d-M-y', "18-Jul-46");
$date->format('d/m/Y');

Earlier also tried,

$date = date('d/m/Y', strtotime('18-Jul-46'));

None of them gave me the correct format. Any pointers or help is appreciated.

Thanks in advance!

  • 4
    Try using a 4 digit year. Anything with 2 digits is treated as after 1970, aka the Unix Epoch (January 1 1970 00:00:00 GMT). – aynber Jan 08 '19 at 18:22

2 Answers2

1

If you have a date such as '31-Dec-18", it is ambiguous since it may refer to a date in 1918 or else a date in 2018. However, if you know that all the dates refer to the 1900s, then code such as the following is feasible given a two-digit year:

<?php
$now = new DateTime();
$formatted = "";
$arrFormattedBDays = [];
$birthdays = ['18-Jul-46','19-Aug-47','1-Jan-19','31-Dec-18'];
foreach ($birthdays as $b){
   list($d,$m,$y) = explode("-",$b);
   $y = '19'.$y;
   $dt = new DateTime("$d-$m-$y");
   $formatted = $dt->format('d/m/Y');
   $arrFormattedBDays[] = $formatted;
}
var_dump($arrFormattedBDays);

Output:

array(4) {
  [0]=>
  string(10) "18/07/1946"
  [1]=>
  string(10) "19/08/1947"
  [2]=>
  string(10) "01/01/1919"
  [3]=>
  string(10) "31/12/1918"

See live code

Otherwise, by default DateTime creates a date object based on the current year which you may format according to the truth you seek to perpetuate; see here. Note: if you know that the dates all occur in the 20th century, i.e. 1901-2000, then you may amend this code by adding in a little logic; see here.

slevy1
  • 3,797
  • 2
  • 27
  • 33
0

The computer doesn't know whether you mean 2000 or 1900. You can just take the last 2 digits of the year and put "19" before like:

$date = new DateTime("18-Jul-46");
$date->format('d/m/19y');

If you want to use 2000 as well, this code will use the closest number to 1970

$date = new DateTime("18-Jul-20");
$date->format('d/m/Y');
$t1 = $date->format('19y');
$t2 = $date->format('20y');

if(abs(1970-$t1)<abs(1970-$t2))
    echo $t1; //Take the 19.. one
else
    echo $t2; //Take the 20.. one

But in the end, you can't be sure that even 2030 would be correct.

Updater
  • 459
  • 2
  • 13
  • 1
    Thanks for your reply! However, I don't think I can blindly add 19 to the string as I maybe dealing with dates starting in 2000s too like 2016 so maybe a manual check to know if it's before 1970? It all seems manual but if is the only way out then could do. – user7616631 Jan 08 '19 at 18:30
  • @user7616631 if your data can't be trusted then no code will work for you – Andreas Jan 08 '19 at 18:33
  • The only thing you can do is to check whether the year is closer to a specific year (e.g. 1970) with 20 before or with 19 before – Updater Jan 08 '19 at 18:38
  • @user7616631 "I maybe dealing with dates starting in 2000s too like 2016" Then how do you know for sure that "18/07/2046" from your question is incorrect? If you have specific logic that you are applying to know that, then you would need to apply the same logic in your code. – Patrick Q Jan 08 '19 at 18:40