Don't click here unless you want to be banned.

LSL Wiki : llGetTimestamp

HomePage :: PageIndex :: RecentChanges :: RecentlyCommented :: UserSettings :: You are crawl338.us.archive.org
string llGetTimestamp()

Returns the current time-and-date (a timestamp) in the format YYYY-MM-DDThh:mm:ss.ff..fZ, for example: 2004-08-27T00:56:21.785886Z
The letter Z stands for Zulu, the military time zone name for UTC. T is just a separator between date and time.

This format allows exact times and easy sorting, but is not as suited for comparing time as a libc like timestamp. Nevertheless, it is still possible. (See below.)

This format is one of the options defined by International Standard ISO 8601 (summary). It is also used to represent a specific instant in time in the XML Schema standard's dateTime data type, which is "inspired" by ISO 8601. As such, this is a format for storing in databases and log files, not display to users or computation.

To get the number of seconds elapsed since 00:00 hours, Jan 1, 1970, use llGetUnixTime. This function is better suited to comparing time than llGetTimeStamp.

The following example shows how hours, minutes, and seconds can be extracted from the timestamp.
//A function that returns a vector in the form of <hours,minutes,seconds> using llGetTimestamp()
//  Keknehv Psaltery 06/15/05
vector time()       //Returns a vector with the current time in hours, minutes, and seconds
{                   //In the format <hours,minutes,seconds>
    list timestamp = llParseString2List( llGetTimestamp(), ["T",":","Z"] , [] );
    return <    llList2Float( timestamp, 1 ),
                llList2Float( timestamp, 2 ),
                llList2Float( timestamp, 3 ) >;
}

AlexanderDaguerre disagrees with the comment about this being an unsuitable format for comparing time; this is one of the things that this format was intentionally designed to support and is the reason that sorting works. Comparing two llGetTimestamp strings should give you the same results as comparing the two instants in some high precision integer format (higher precision than Unix timestamp format, too). Of course, with that decimal point in there you shouldn't compare two such strings for equality for the same reasons that you should never expect two floating-point values to compare equal. AlexanderDaguerre agrees with Ezhar that this format is pretty hard to use for time difference as opposed to comparison.

"AlericInglewood notes that operator < is not defined for strings, hence it is indeed non-trivial to compare two llGetTimestamp strings. The following code does the job however:"
// Comparison function for strings returned by llGetTimestamp.

// Returns 0  if the date/times are equal.
// Returns -1  if the first string (a) is less (earlier) than the second (b).
// Returns 1 if the first string (a) is larger (later) than the second (b).
//
integer TimestampCmp(string a, string b)
{
  list la = llParseString2List(a, ["-", "T", ":", "Z"], []);
  list lb = llParseString2List(b, ["-", "T", ":", "Z"], []);
  integer i;
  for (i = 0; i < 6; ++i)
  {
    float fa = llList2Float(la, i);
    float fb = llList2Float(lb, i);
    if (fa != fb)
    {
      if (fa < fb)
        return -1;
      else
        return 1;
    }
  }
  return 0;
}

Ezhar would like an easy way to tell the time difference between two timestamps, which is very simple in UNIX timestamps but not in this format (at least not using LSL).
I just scraped together a function that might do what you ask Ezhar... there may be a couple bugs with it, namely in dealing with leap-years and varying days in months, but that's because I wrote it in 10 mins. I would fix them, but its 3AM and Im tired :) -Chris
// float secsBetween(string, string):
// A very rough way of getting the difference in seconds
// between two timestamps in the form returned by llGetTimestamp. 
// Note that this function currently has two problems:
//    1. No accurate leap-year correction.
//    2. No accurate month-day correction (30 days, 31 days, etc)
// Both are fixable, but Im currently too sleepy :)
// Written by:     Christopher Omega
// Date:        9/4/04 
float secsBetween(string t1, string t2) {
    // Parses the timestamps into a two-element list consisting of
    // [date, time] where date is a string in the form "YYYY-MM-DD"
    // and time is a string in the form "hh:mm:ssZ" (Note: ss is a float value)
    list parsed1 = llParseString2List(t1, ["T"], []);
    list parsed2 = llParseString2List(t2, ["T"], []);
    
    // Date1 and Date2 are lists in the form of [year, month, day]
    list date1 = llParseString2List(llList2String(parsed1, 0), ["-"], []);
    list date2 = llParseString2List(llList2String(parsed2, 0), ["-"], []);
    
    // Time1 and Time2 are lists in the form of [hours, minutes, seconds]
    // Taking into account the one-letter "Z" suffix on the end of the time element 
    // by deleting it.
    list time1 = llParseString2List(llDeleteSubString(llList2String(parsed1, 1), -1, -1), [":"], []);
    list time2 = llParseString2List(llDeleteSubString(llList2String(parsed2, 1), -1, -1), [":"], []);
    
    // Stamp* lists are in the form [year, month, day, hour, min, sec]
    list stamp1     = date1 + time1;
    list stamp2     = date2 + time2;
    
    // SECONDS_CONVERSION is a list containing the number of seconds in:
    // one year, one month, one day, one hour, one minute and one second,
    // respectively.
    // TODO: Provide accurate leap-year and month-day-count correction.
    // Im assuming 365.25 days in a year and 30 days in a month :(
    list SECONDS_CONVERSION = [31557600, 2592000, 86400, 3600, 60, 1];
    
    float diffInSecs = 0;
    integer i;
    for (i = 0; i < 6; ++i) {
        // TODO: See if extracting elements as floats here is a reasonable 
        // accuracy tradeoff.
        // Thought: Perhaps we could multiply the seconds
        // value by some power of ten at the beginning of this function
        // and simply work with it like you would an integer, since its the only 
        // floating point value.
        float element1             = (float) llList2String(stamp1, i);
        float element2             = (float) llList2String(stamp2, i);
        float conversionFactor     = (float) llList2String(SECONDS_CONVERSION, i);
        
        diffInSecs += llFabs(element1 - element2) * conversionFactor;
    }
    
    return diffInSecs;
}


I was researching information on dates here and noticed that the statement below was innacurate. Every 100 years is /NOT/ a leap year, except for every 400 years, which /ARE/ a leap year. See (http://mathforum.org/dr.math/faq/faq.calendar.html) for more information. - RichardSolvang

My bad - Ice

Here's another stab at a timestamp-difference function. It doesnt use any kind of zero reference point, so as long as the two times are close enough to one another, the function should handle them fine. It works like the difference operator, subtracting the second parameter from the first - so if the second timestamp is farther into the future then the first (has a larger time value), then it will return a negative value. It should handle month-days and leap years much better then my previous try, but to do so, the code grew a great number of lines. Be careful though, I havent rigorously tested it. -Chris
// Scroll down...
integer min(integer a, integer b) {
    if (a > b)
        return b;
    return a;
}

integer isLeapYear(integer year) {
    return (year % 4 == 0 && (year % 100 != 0 || year % 400 == 0));
}

integer daysInMonth(integer month, integer year) {
    if (month < 9) {
        if (month != 2) {
            // Before September, odd numbered months
            // are 31 days long.
            if (month % 2 != 0) {
                return 31;
            } else {
                return 30;
            }
        } else {
            // February is the odd man out.
            if (isLeapYear(year)) {
                return 29;
            } else {
                return 28;
            }
        }
    } else {
        // After August, odd numbered months
        // are 30 days long.
        if (month % 2 != 0) {
            return 30;
        } else {
            return 31;
        }
    }
}

// timestampDiff(string, string)
// Written by Christopher Omega 10/21/05
// Returns the difference between the two timestamps
// passed to it, subtracting the second parameter from
// the first. 
float timestampDiff(string t1, string t2) {
    if (t1 == t2) 
        return 0;
    
    float diff = 0;
    integer year1 = (integer) llGetSubString(t1, 0, 3);
    integer year2 = (integer) llGetSubString(t2, 0, 3);
    integer i;
    if (year1 != year2) {
        integer minYear = min(year1, year2);
        integer maxYear = year1;
        if (minYear == year1)
            maxYear = year2;
        float secsBetween;
        secsBetween += 31536000 * (maxYear - minYear);
        for (i = minYear; i < maxYear; ++i) {
            if (isLeapYear(i))
                secsBetween += 86400; // Add extra day.
        }
        if (year2 == maxYear)
            secsBetween *= -1;
        diff += secsBetween;
    }
    
    integer month1 = (integer) llGetSubString(t1, 5, 6);
    integer month2 = (integer) llGetSubString(t2, 5, 6);
    if (month1 != month2) {
        integer month1Secs;
        for (i = 1; i < month1; ++i) {
            // 1 day = 24 hrs * 60 mins * 60 secs
            month1Secs += daysInMonth(i, year1);
        }
        month1Secs *= 86400; // Convert days into secs.
        integer month2Secs;
        for (i = 1; i < month2; ++i) {
            month2Secs += daysInMonth(i, year2);
        }
        month2Secs *= 86400;
        diff += month1Secs - month2Secs;
    }
    // Whew! Now everything past this point should be clear cut
    // conversion directly into seconds.
    integer days1 = (integer) llGetSubString(t1, 8, 9);
    integer days2 = (integer) llGetSubString(t2, 8, 9);
    diff += (days1 - days2) * 86400;
    integer hours1 = (integer) llGetSubString(t1, 11, 12);
    integer hours2 = (integer) llGetSubString(t2, 11, 12);
    diff += (hours1 - hours2) * 3600; //1 hr = 60 mins * 60 secs.
    integer minutes1 = (integer) llGetSubString(t1, 14, 15);
    integer minutes2 = (integer) llGetSubString(t2, 14, 15);
    diff += (minutes1 - minutes2) * 60;
    float secs1 = (float) llGetSubString(t1, 17, -2); // Skip last char.
    float secs2 = (float) llGetSubString(t2, 17, -2);
    diff += secs1 - secs2;
    return diff;
}

The scripts at LibraryTimeElapsed use this function to compare points in time with high accuracy.



My version of this, since all the others didn't seem to cut it fully enough for my uses - Escort

// Take a timestamp and return it in PST string format
// Example of the output format is "Sun 7/15/2007 1:02 pm"
string timestamp2PST(string timestamp) {
    // Set up constants required for the function (could be made global)
    list weekday_names = [ "Saturday", "Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday" ];
    list days_in_month = [31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31];
    
    // Parse the timestamp
    list parts = llParseString2List(timestamp, ["-", "T", ":", ".", "Z"], []);
    
    // If it's not a timestamp, then just return the original string
    if (llGetListLength(parts) != 7) {
        return timestamp;
    } else {
        // Set up the local variables we need
        integer year = llList2Integer(parts, 0);
        integer month = llList2Integer(parts, 1);
        integer day = llList2Integer(parts, 2);
        integer hour = llList2Integer(parts, 3);
        integer minute = llList2Integer(parts, 4);
        integer second = llList2Integer(parts, 5);
        
        // Account for time difference from simulator to UTC->PST
        integer difference = (integer)((llGetWallclock() - llGetGMTclock()) / 3600);
        if (difference > 0) {
            difference -=24;
        }        
        hour += difference;

        // Deal with day/month/year boundaries crossed by the adjustment for the time difference
        if (hour < 0) {
            day--;
            hour += 24;
            if (day <= 0) {
                month--;
                if (month <= 0) {
                    year--;
                    month += 12;
                }

                day = llList2Integer(days_in_month, month - 1);
                
                // Do a leap year adjustment if required
                if (month == 2 && year % 4 == 0 && (year % 100 != 0 || year % 400 == 0)) {
                    day++;
                }
            }
        }
        
        // Determine the day of the week
        // This highly non-intuitive code is based on an algorithm 
        // from http://mathforum.org/library/drmath/view/55837.html
        if (month < 3) {
            month += 12; 
            --year;
        }
        integer weekday_number = (day + 2 * month + (3 * (month + 1)) / 5
            + year + year / 4 - year / 100 + year / 400 + 2) % 7;
        
        if (month > 12) {
            month -= 12;
            ++year;
        }
    
        // Build the PST date string (fixed format)
        string date = llGetSubString(llList2String(weekday_names, weekday_number), 0, 2);
        date += " " + (string)month + "/" + (string)day + "/" + (string)year;
        
        // Convert the hour to am/pm
        string suffix = " pm";
        if (hour < 12) {
            suffix = " am";
            if (hour == 0) {
                hour = 12;
            }
        } else if (hour > 12) {
            hour %= 12;
        }
        
        date += " " + (string)hour + ":";
        if (minute < 10) {
            date += "0" + (string)minute;
        } else {
            date += (string)minute;
        }
        date += suffix;
        return date;
    }
}


This article wasn't helpful for you? Maybe the related article at the LSL Portal is able to bring enlightenment.

Functions | Time | Timestamp | Jasa SEO Murah Jasa SEO Jasa Google Adwords Jasa Adwords Google Adwords Sepatu Safety Sepatu Futsal Cheapes Hostgator Coupon Link Booking Televisori offerte Notebook Offerte Govr Edo Ziedo Portatile Apple RDAnet Lorks Karikatur Bisnis Modal Kecil Bisnis UKM Berita Terbaru Iklan Baris Jasa SEO Murah SEO Indonesia Konsultan SEO SEO Belajar SEO Penumbuh Rambut Kursus SEO Jam Tangan Casio Grosir Baju Bisnis Online Kerupuk Kulit Social Bookmark Kumpulan Puisi WBC Wonogiri Penumbuh Rambut Jam Tangan Murah Jam Tangan Murah Jam Tangan Casio Penumbuh Rambut Kerupuk Kulit Alat Kantor Laku.com Belanja Online Grosir Eceran Murah dan Aman Jasa SEO Model Jilbab Fine Tableware Permanent Hair Removal island investment development professional makeup artist bali private villa sewa mobil jakarta murah Jual rumah Jakarta Contact Lens Technology
There are 5 comments on this page. [Display comments/form]