Last active
July 2, 2023 16:47
-
-
Save ExcelRobot/249f1d057152cf5243af894d2e0965a4 to your computer and use it in GitHub Desktop.
Humanize Seconds LAMBDA Function
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/* | |
These lambdas were inspired by the work of Mike Wolfe's article "Displaying Human | |
Readable Time Spans" (https://nolongerset.com/displaying-time-spans/). He provided | |
the logic and I enjoyed the puzzle of converting that logic to dynamic arrays. | |
Included within: | |
* HUMANIZESECONDS - Converts seconds to human readable text | |
* PLURALIZE - Adapts wording based on whether number is singular/plural and | |
positive/negative. | |
* CONVERTTOSECONDS - Converts units of years, weeks, days, hours, minutes, and | |
seconds to total seconds. | |
*/ | |
/* | |
Name: Humanize Seconds (HUMANIZESECONDS) | |
Description: Converts number of seconds to a human readable text broken down by years, | |
weeks, days, hours, minutes, and seconds. | |
Dependencies: PLURALIZE, CONVERTTOSECONDS | |
Author: Excel Robot (@ExcelRobot) | |
Inspired By: Mike Wolfe (https://nolongerset.com/displaying-time-spans/) | |
Category: Time | |
*/ | |
HUMANIZESECONDS = LAMBDA(seconds,LET( | |
SecondsPerMinute, 60, | |
SecondsPerHour, SecondsPerMinute*60, | |
SecondsPerDay, SecondsPerHour*24, | |
SecondsPerWeek, SecondsPerDay*7, | |
SecondsPerYear, SecondsPerDay*365, | |
Years, INT(seconds/SecondsPerYear), | |
Weeks, LET(x,INT((seconds-Years*SecondsPerYear)/SecondsPerDay),IF(MOD(x,7)=0,x/7,0)), | |
Days, INT((seconds-Years*SecondsPerYear-Weeks*SecondsPerWeek)/SecondsPerDay), | |
Hours, INT((seconds-Years*SecondsPerYear-Weeks*SecondsPerWeek-Days*SecondsPerDay)/SecondsPerHour), | |
Minutes, INT((seconds-Years*SecondsPerYear-Weeks*SecondsPerWeek-Days*SecondsPerDay-Hours*SecondsPerHour)/SecondsPerMinute), | |
Secs, seconds-Years*SecondsPerYear-Weeks*SecondsPerWeek-Days*SecondsPerDay-Hours*SecondsPerHour-Minutes*SecondsPerMinute, | |
PluralWording, {"# year[s]";"# week[s]";"# day[s]";"# hour[s]";"# minute[s]";"# second[s]"}, | |
Nums, CHOOSE(SEQUENCE(6),Years,Weeks,Days,Hours,Minutes,Secs), | |
Pluralized, MID(REDUCE("",SEQUENCE(ROWS(PluralWording)),LAMBDA(tot,x,tot&IF(INDEX(Nums,x,1)=0,"",", "&PLURALIZE(INDEX(PluralWording,x,1),INDEX(Nums,x,1))))),3,999), | |
Pluralized | |
)); | |
/* | |
Name: Pluralize (PLURALIZE) | |
Description: Combines a number with a wording template string to adapt the wording to | |
whether the number is singular/plural and positive/negative. Text in brackets [s] | |
will only be shown if plural, unless a / is included to specify different text for | |
singular/plural [y/ies]. Text in braces is show based on number being positive/negative | |
{gain/loss}. If a num_token is not specified, # will be used. If a num_format is not | |
specified, general formatting will be used. | |
Author: Excel Robot (@ExcelRobot) | |
Inspired By: Mike Wolfe (https://nolongerset.com/displaying-time-spans/) | |
Category: Words | |
*/ | |
PLURALIZE = LAMBDA(text,num,[num_token],[num_format],LET( | |
fnGetGroups, LAMBDA(txt,quoted_delimiter,LET( | |
chars, MID(txt,SEQUENCE(LEN(txt)),1), | |
seq, SEQUENCE(ROWS(FILTER(chars,chars=LEFT(quoted_delimiter)))), | |
start, FIND(CHAR(160),SUBSTITUTE(txt,LEFT(quoted_delimiter),CHAR(160),seq)), | |
chargroup, MID(txt,start,FIND(RIGHT(quoted_delimiter),txt,start)-start+1), | |
chargroup | |
)), | |
BracketGroups, fnGetGroups(text,"[]"), | |
BraceGroups, fnGetGroups(text, "{}"), | |
DividingSlash, "/", | |
IsPlural, ABS(num)<>1, | |
IsNegative, num<0, | |
fnGetReplacements, LAMBDA(groups,divider,use_secondary,LET( | |
finddivider, FIND(divider,groups), | |
nodivider, IF(use_secondary,MID(groups,2,LEN(groups)-2),""), | |
withdivider, IF(use_secondary,MID(groups,finddivider+1,LEN(groups)-finddivider-1),MID(groups,2,finddivider-2)), | |
replacement, IF(ISERROR(finddivider),nodivider,withdivider), | |
replacement | |
)), | |
BracketReplacements, fnGetReplacements(BracketGroups,DividingSlash,IsPlural), | |
BraceReplacements, fnGetReplacements(BraceGroups,DividingSlash,IsNegative), | |
ReplaceNumToken, SUBSTITUTE(text,IF(OR(ISOMITTED(num_token),num_token=""),"#",num_token),IF(OR(ISOMITTED(num_format),num_format=""),num,TEXT(num,num_format))), | |
ReplaceBracketGroups, IFERROR(REDUCE(ReplaceNumToken,SEQUENCE(ROWS(BracketGroups)),LAMBDA(tot,x,SUBSTITUTE(tot,INDEX(BracketGroups,x),INDEX(BracketReplacements,x)))),ReplaceNumToken), | |
ReplaceBraceGroups, IFERROR(REDUCE(ReplaceBracketGroups,SEQUENCE(ROWS(BraceGroups)),LAMBDA(tot,x,SUBSTITUTE(tot,INDEX(BraceGroups,x),INDEX(BraceReplacements,x)))),ReplaceBracketGroups), | |
ReplaceBraceGroups | |
)); | |
/* | |
Name: Convert To Seconds (CONVERTTOSECONDS) | |
Description: Converts units of years, weeks, days, hours, minutes, and | |
seconds to total seconds. | |
Author: Excel Robot (@ExcelRobot) | |
Inspired By: Mike Wolfe (https://nolongerset.com/displaying-time-spans/) | |
Category: Time | |
*/ | |
CONVERTTOSECONDS = LAMBDA(years,weeks,days,hours,minutes,seconds,LET( | |
SecondsPerMinute, 60, | |
SecondsPerHour, SecondsPerMinute*60, | |
SecondsPerDay, SecondsPerHour*24, | |
SecondsPerWeek, SecondsPerDay*7, | |
SecondsPerYear, SecondsPerDay*365, | |
TotalSeconds, years*SecondsPerYear+weeks*SecondsPerWeek+days*SecondsPerDay+hours*SecondsPerHour+minutes*SecondsPerMinute+seconds, | |
TotalSeconds | |
)); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment