Section loop starts with wrong index/value - smarty

I`d like to fill a select box for year of birth with the years starting with the current year -18 and then 100 years backwards. Somehow the loop starts with 2000 and not 2001.
When I use the smarty.now funtion and substract 18 years from it, it will result in 2001 which is correct.
But when I use the same function in a section loop and step -1, the loop will start with 2000 and not 2001.
I could use -17 in the section loop but I`d like to understand why there seems to be an offset of 1 here even if the default value for start is 0 according to the documentation.
{$smarty.now|date_format:"%Y"-18}
{* Result is 2001 as expected *}
<br>
{section name=bar loop=$smarty.now|date_format:"%Y"-18 max=100 step=-1}
{$smarty.section.bar.index}
{/section}
{* Loop starts with 2000,1999... why? *}

It's because in your date_format , you put step = -1 .
Smarty execute this step in the section before displaying the first value. So, the section will be like that :
2000
1999
1998
..

Related

Moving average conditioned in Google Sheets

I have a Google Sheet in which I have to calculate a moving average conditioned to the 'ID' that calculates the average of the last 3 periods.
Any idea on how to do it?
I leave an example with the final results (column "Mean Average (last 3)").
Regards!
ID value Mean Average (last 3)
1 12 12,00
1 19 12,00
1 19 15,50
1 18 16,67
1 13 18,67
2 11 11,00
2 18 11,00
2 15 14,50
2 17 14,67
2 11 16,67
3 11 11,00
3 16 11,00
3 10 13,50
3 11 12,33
I've got an answer that may work for you. Assuming that your sample data is in columns A4:C (see my sample sheet), try the following formula in column D, in the same row as your data headers.
={"Mean Avg";ArrayFormula(
IF(ROW(A4:A18)<ROW(A$4)+2,
C$4,
IF(NOT(EQ(A4:A18,OFFSET(A4:A18,-1,0))),
B4:B19,
IF(NOT(EQ(A4:A18,OFFSET(A4:A18,-2,0))),
B3:B18,
IF(NOT(EQ(A4:A18,OFFSET(A4:A18,-3,0))),
(B2:B17+B3:B18)/2,
(B1:B16+B2:B17+B3:B18)/3)))))}
The first IF checks whether it is one of the first two data rows, to force the initial values.
The next IF checks if the ID is not equal to the row above, and forces the start of a new Average, with just one value. The next IF checks if it is the second ID in a series (NOT EQual to the ID 2 rows up), and if yes, also uses the single value from the row above.
The next IF checks up three rows, and if the IDs are different, it averages the values from the two rows above.
Otherwise, this is the fourth data row in a series with the same ID, and the formula takes the values from the three rows above, and averages them.
Due to the offsets, it seems quite sensitive to ranges, so it may need some tuning if you move it.
Let me know if this helps.

MapReduce, to extract the one row with highest value

This is the result(actula output) for reducer. The data is title(key),month and frequency of how many books are borrowed based on the book title(value), and Is there any way to get the only one row with highest value? For example, I want to choose the only row with highest frequency among lots of rows. If you know the way, please enlighten me. Thanks a lot.
"""E"" is for evidence [sound recording] / by Sue Grafton." 05 8
"""F"" is for fugitive [sound recording] / by Sue Grafton." 05 6
"""G"" is for Grafton : the world of Kinsey Millhone / Natalie Hevener Kaufman and Carol McGinnis Kay." 06 1
"""G"" is for gumshoe [text (large print)] / Sue Grafton." 09,10 1
"""Galapagos"" means ""tortoises"" / written and illustrated by Ruth Heller." 10,04,09 2
"""Git on board 09 1
"""God's banker"" / by Rupert Cornwell." 05,10,11 1
"""Gospodi-- spasi i usmiri Rossi︠i︡u"" : Nikolaĭ II 10,11 1
"""H"" is for homicide [sound recording] / by Sue Grafton." 12 4
Run a secondary mapreduce job accepting as input, the output of the first action. The values to write in the Mapper could be (NullWritable, line), as you want to collect all lines to a single reducer, but you don't really care about a key otherwise, then parse out the number of each line, keeping track of the current maximum value and its associated line. After looping over all values, write the maximum line.
To improve the run time of this process, use setCombinerClass in your job configuration to use this new reducer

Making complex new variables

I have troubles finding a solution to the following problem:
I have an age variable (e.g. 18, 20, 56) and a date when the survey was taken (2012). What I want to do is the following: if the respondent is 10 years old I need to make 10 categories of age with 0 and 1 when the respondent was not existing or alive: so new variable age2002 = 1, age2003 = 1, ... age2012 = 1 but age2000 = 0 and age1990 = 0.
How can I do this is in spss syntax for every respondent? I have many varying ages but the year of the survey is always the same.
this is for all the ages from 1 to 100:
do repeat NewVr=age1912 to age2012/vl=1912 to 2012.
compute NewVr=(2012-age<=vl).
end repeat.
execute.
if you only want all the ages between 1 to 10 and then 2000, 1990, 1980 etc':
do repeat NewVr=age1970 age1980 age1990 age2000 age2002 to age2012
/vl=1970 1980 1990 2000 2002 to 2012.
compute NewVr=(2012-age<=vl).
end repeat.
execute.
What is the actual problem you are attempting to solve? Creating a bunch (100) 0/1 dummy variables doesn't seem like a very sound data management practice.
If you do go with the suggested
DO REPEAT ...
compute NewVr=(2012-age<=vl).
....
I would rewrite that as
COMPUTE newvar= ( (2012-age ) LE v1 ).
just seems clearer to parse in my brain.

Calculating year dummy variables using a for loop (foreach) in Stata

I am attempting to generate a dummy variable for each year from 1996 to 2012 (inclusive) such that the 1996 dummy should equal 1 if it is 1996 and 0 if else using the foreach command in Stata to cut down on time (at least for future projects). What is currently happening is that the dummy for 1996 is being produced, but no others are generated.
I think that it has to do with how I am defining j, but I cannot quite figure out the formatting to achieve the results that I want. I have looked online and in the Stata help files and cannot find anything on this specific topic.
Here is what I have thus far:
local var year
local j = 1996
foreach j of var year {
gen d`j' = 1 if year==`j'
local ++j
}
I will continue to try and figure this out on my own, but if anyone has a suggestion I would be greatly appreciative.
Let us look at this line by line.
local var year
You defined a local macro var with content "year". This is legal but you never refer to that local macro in this code, so the definition is pointless.
local j = 1996
You defined a local macro j with content "1996". This is legal.
foreach j of var year {
You open a loop and define the loop index to be j. That means that within the loop any reference to local macro j will be interpreted in terms of the list of arguments you provide. (The previous definition of j is irrelevant within the loop, and so has no effect in the rest of your code.)
... of var year
You specify that the loop is over a variable list here. Note that the keyword var here is short for varlist and has absolutely nothing to do the local macro name var you just defined. The variable list consists of the single variable name year.
gen d`j' = 1 if year==`j'
This statement will be interpreted, the one and only time the loop is executed, as
gen dyear = 1 if year==year
as references to the local macro j are replaced with its contents, the variable name year. year==year is true for every observation. The effect is a new variable dyear which is 1 in every observation. That is not an indicator or dummy variable as you want it. If you look at your dataset carefully, you will see that is not a dummy variable for year being 1996.
local ++j
You are trying to increment the local macro j by 1. But you just set local macro j to contain the string "year", which is a variable name. But you can't add 1 to a string, and so the error message will be type mismatch. You don't report that error, which is a surprise. It is a little subtle, as in the previous command the context of generate allows interpretation of the reference to year as an instruction to calculate with the variable year, which is naturally numeric. But local commands are all about string manipulation, which may or may not have numeric interpretation, and your command is equivalent, first of all, to instructing Stata to add
"year" + 1
which triggers a type mismatch error.
Turning away from your code: Consider a loop
forval y = 1996/2012 {
gen d`y' = 1 if year == `y'
}
This is closer to what you want but makes clearer another bug in your code. This would create variables d1996 to d2012 but each will be 1 in the year specified but missing otherwise, which is not what you want.
You could fix that by adding a further line in the loop
replace d`y' = 0 if year != `y'
but a much cleaner way to do it is the single line
gen d`y' = year == `y'
The expression
year == `y'
is evaluated as 1 when true and 0 when false, which is what you want.
All this is standard technique documented in [U] or [P].
As #Roberto Ferrer pointed out, however, experienced Stata users would not define dummies this way, as tabulate offers an option to do it without a loop.
A tutorial that brings together comments on local macros, foreach and forvalues loops is within http://www.stata-journal.com/sjpdf.html?articlenum=pr0005
search foreach
within Stata would have pointed to that as one of various pieces you can read.
Looping is not necessary. Try the tabulate command with the gen() option. See help tabulate oneway.
See also help xi and help factor variables.
You are trying to loop through the distinct values of year but the syntax is not correct. You are actually looping through a list of variables with only one element: year. The command levelsof gives you the distinct values, but like I said, looping is not necessary.
Maybe this might help.
/*assuming the data is from 1970-2012*/
/*assuming your year variable name is fyear*/
forvalues x=1970/2012 {
gen fyear `x'=0
replace fyear `x'=1 if fyear==`x'
}
However, I do agree with Roberto Ferrer that loop may not be necessary.

Performing multiple operations if condition is satisfied in ternary operator in linq

I am a beginner in LINQ.I want to perform some conditional operation lik follows,
(from emp in Employees
let DOB=emp.BirthDate.GetValueOrDefault()
let year=DOB.Year
let month=DOB.Month
let EmpAgeInYearsToday=DateTime.Now.Year-year
let EmpAgeInMonthToday=DateTime.Now.Month-month
let temp_year=(EmpAgeInYearsToday-1)
let ExactNoOfMonths_temp=EmpAgeInMonthToday<0?temp_year:EmpAgeInMonthToday
let ExactNoOfMonths=EmpAgeInMonthToday<0?EmpAgeInMonthToday+12&temp_year:EmpAgeInMonthToday
select new{emp.EmployeeID,DOB,
EmployeeAgeToday=EmpAgeInYearsToday+" Years "+ExactNoOfMonths+" Months ").Dump();
Here,
let ExactNoOfMonths=EmpAgeInMonthToday<0?EmpAgeInMonthToday+12&temp_year:EmpAgeInMonthToday
This part is not working. The expression in the left side of & alone is getting executed.I want to perform both the operations. How to achieve this?How to perform multiple operations when the condition is satisfied?
Is there any Other alternate way for doing this?
I think what you mean is something like this:
ExactNoOfMonths = EmpAgeInMonthToday < 0 ?
EmpAgeInMonthToday + 12 :
temp_year ?
EmpAgeInMonthToday :
somethingElse
but there should be a third value (somethingElse) for when EmpAgeInMonthToday >= 0 and temp_year = false.
Edit
What you want is actually pretty complicated. You better just fetch the dates of birth in memory and do the calculation in plain C#.
This CodeProject link gives a possible approach. As you'll see you can't avoid leap years and month lengths: the difference between Feb 28 and Mar 28 is 1 month in a normal year, 1 month and 1 day in a leap year.

Resources