-2

It is my first post here and I thought it really fits on this side than on the regular website.

I am sure many of you (programmers) must have had nightmares with this Date 'object', either in your early days or in some code you are inheriting from someone. Let's just assume there are more programmers in then rest of the world (6.6 billion) than in the US (0.4 billion)! :)

So, if you are programming from outside the US, you most likely have a date format different from the default computer (US) format, ie, different from 2019 11 28 02:03:04. So a lot of the times, you got this date wrong: 11 04 2019... well it is 11th April for 'most of us', and 4th November for Americans.

I thus, decided, against what all programmers here may scream against, that I will declare my dates as string:

Dim StartDate As String = String.Empty

This works wonders for me because when I send my dates to the database (Access, SQL CE, SQL Server, MySql, ie, the databases I ever program against), I send them as String, thus: '11 Apr 2019'. Replace ' with # for Access.

All my databases are happy. All my programmers/partners are happy reading the code, there is no confusion about 11 Apr 2019.

This works great for Create, Retrieve, Update (you can add Delete).

So my question is, why do we have to be 'conventional' and declare our variables as Date, when that is causing most of the world a lot of trouble?

Is it thus possible to create a new data type that will take care of this, so that it is not String, as I'm sure a lot of you will protest against my use of String?

So while this appeal is pending, I continue to display dates in all my applications as:

Start Date: 29 Nov 2019

, which Germans and Americans will be slightly annoyed about, but be able to read without any ambiguity, and send them for search/update/insert as

StartDate = '29 Nov 2019 00:00:00'

I know there are Regional and Globalization classes to use, but in Africa (1.2billion), a huge chuck would not even set their computer regions right. Please don't think they way you are thinking: internet is still an invention out there for the majority - penetration rate on PCs is barely climbing to 10%!

My 'ComplexDate' data type would be one that requires month part of the date to be specified in String, as you have seen in my examples above. So that we are all clear on which date this post was made! eg, Nov/2/2019, 02/Nov/2019, 2019/Nov/2, 5 Nov 2019, etc

4
  • 1
    The date 04 Nov 2019 is less ambiguous than 11/04/2019, but it is still ambiguous. Depending on the timezone, 04 Nov 2019 23:30:00 and 05 Nov 2019 00:30:00 may be the same point in time. Using a concrete Date class allows you to add a field with the offset to UTC, which would resolve all ambiguities. And then it does not matter whether you store the month as string or as integer (or as enum). Commented Nov 29, 2019 at 14:18
  • 3
    There is nothing inherently wrong with coding dates as strings, where it makes sense. But what is your question? Commented Nov 29, 2019 at 14:21
  • 2
    A date is a date is a date. If you're messing up while interpreting Date Objects, something very wrong is going on in your code and this isn't your biggest problem. Commented Nov 29, 2019 at 17:07
  • "I continue to display dates in all my applications as [...]". Display and internal representation aren't directly related. You can display strings using whatever format you want and store them in an entirely different structure. Commented Nov 29, 2019 at 21:06

4 Answers 4

6

A date is a date.

A string can be the representation of a date. A complex object can be another representation of a date. Regardless of the chosen representation, you need to ensure consistency, for example compare two representations in a way to see which date is before the other.

If you chose the string representation: you may want to use ISO 8601 format YYYY-MM-DD. It’s an international and unambiguous standard and has the advantage of facilitating comparison and sorting: the ordinary string comparison is consistent with the date comparison, provided you do not skip the leading zeros.

The numeric MM also has the advantage of avoiding language localisation issues (e.g. "Apr." is "Avr." in French and "Oct." is "Okt." in German). You may still easily convert for diplaying in the format expected by the user.

2
  • Another part of it... actually I have adopted this for a long time that I manage wriggle my way around easily around it. So to compare: Date.Compare(CDate("2 Nov 2019"), CDate("4 Nov 2018")). I always fetch my date results as CDate(EndDate).ToString("dd MMM yyyy"). Helpful, eg, when I am stepping through my code. I just have to write a little more than I think is necessary with a new Data Type... it is another training, pain, that I have to take my interns through! Commented Nov 29, 2019 at 13:02
  • 2
    @HanningtonMambo Interesting. But isn’t CDate() making the conversion based on the regional setting of the computer ? I’d recommend to check because CDate(“4/7/2019”) would then be 4th of July in dd/mm/yyyy countries and 7th April in US and other mm/dd/aaaa coutries; furthermore “4 Oct. 2019” would fail to convert in some languages for example in Germany, where “4 Okt. “ would be the correct spelling. Commented Nov 29, 2019 at 14:56
2

Like Christophe said a date is a date. Also by storing stringified dates you are effectively introducing issues within your system. Do you ever need to sort your data on date or filter only a certain range? Every query you will write will have to have conversions back to date or other number format in order to get the results back correctly.

Date is date for a reason. Stringifying a Date should only be done on UI layer.

4
  • I was prompted to write this today because one of my programmers coded a value: StartDate As Date. The value was being submitted to a query in SQL Server, which interpreted '2/11/2019' as '11 Feb 2019'. It took a few hours to discover this. Which is why, as I said earlier, I insist on declaring them as strings, then send them as CDate("2 Nov 2019"), even as plane '2 Nov 2019'. We sort from the database, so that poses no problem. Search as StartDate = CDate(StartDate), where in code, StartDate is "2 Nov 2019". Probably seen more in inter-country projects, or as in my country, 'cool' vs others Commented Nov 29, 2019 at 13:55
  • Let me add this was caused by his pc regionalised to US-Time, sending data across to another PC hosting the database set to UK-time format. Got really wierd results. Commented Nov 29, 2019 at 13:59
  • 2
    if your developer had the possibility to insert a date which the db system interpreted to be something you didn't expect. I believe you are having another issue. Possibly sql injection issues. Commented Nov 29, 2019 at 14:00
  • I understand. In one or two occasions somebody may have made concatenation and missed something... And you would also agree this problem starts/occurs more around the date formats. It is easier to catch other problems than this of dates until it is too late! Which is why I WONDERED whether it could be sorted out by a special/new data type... Commented Nov 29, 2019 at 14:08
2

As you've pointed out, interpreting a string as a date can be problematic.

In fact, your question was prompted by some software interpreting "2/11/2019" as "11 Feb 2019".

What are you going to do if you later decide to change the format and have to update all the dates in 100,000 lines of code? Since these are strings, what will you do if your program asks for a date and the user types in "Today"? How far into your code will that bad data get?

A better solution would be to use the date object as it was intended and possibly disallow use of StringToDate() (CDate) functions (because they have to make assumptions)

There is nothing ambiguous about explicitly setting the parts of a date:

myDate.Month = 2
myDate.Day = 11
myDate.Year = 2019

If you have users in different countries, they can all view that date in whatever format they want. They will all agree as to the value of that object. You can easily compare it to others, sort it, filter by it, etc.

I thus, decided, against what all programmers here may scream against, that I will declare my dates as string:

There's a very good reason that experienced programmers are against this. Objects have been around for a long time now because they're useful - they let us store and manipulate data in one format, and display it in another. Squashing a complex object into some arbitrary string format may seem like a good solution to an immediate problem, but it may expose you to other problems not yet anticipated.

0

This issue is not simply storing the date in a string. The issue is reading a date stored as a string and not treating it as you would input.

Strings are a wonderfully portable storage format. XML and JSON are really just big long strings. They are much more human readable than binary. This is what makes them "portable".

That's what you've discovered here. Date strings are portable.

Up to a point. You see XML and JSON have schemas for a reason. "29 Nov 2019" may seem perfectly understandable and correct at a glance but how about 10 of them? 100? 1000? No one is going to carefully read through long lists of these dates and be sure they're free of errors.

So we make programs do it. And that's fine except since there are different ways to represent the date different programs have different ideas how they should be represented. Some innocent programmer puts two of these systems together, sees no errors, and goes home. The problem only becomes apparent after a 3am phone call.

If the date string enforced some schema across programs this wouldn't have happened. If the string date had been treated as input and validated this wouldn't have happened. And if the date had been shoved into some object that did it's own validating and enforced it's type this wouldn't have happened.

I see no reason to force you to use the last option but you have to solve this problem somehow. People tend to push for the last option because being stringly typed makes it hard for readers to tell what is being passed around: input, or trusted data. If you have some other way to solve that problem go ahead. But don't just ignore it.

My point is there is nothing magical about values being stored. Hell while some might say:

Stringifying a Date should only be done on UI layer

I'd say that source code is also a UI layer. You have humans looking at it after all. But seriously it's nice if data doesn't have to be validated again as it passes every single boundary in your code.

If you don't want to treat the DB as an untrusted input device then when you store a date as a string it means every reader of the DB has to check that every writer to that DB now and forever has the same idea of how to express dates. That's not a simple problem to solve unless there are very few writers, forever.

You must weigh that problem against the portability advantage you've found with strings.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.