Buy= abs(Ref(H,-1)-Ref(L,-1)) < Ref(ATR(5),-1) AND abs(Ref(H,-2)-Ref(L,-2)) < Ref(ATR(5),-1) AND abs(Ref(H,-3)-Ref(L,-3)) < Ref(ATR(5),-1);

Now I would like to optimize for number of previous H and L that smaller the ref(atr(5),-1), I assume I can using loop to achieve it, something like......

The optimize function works ONLY in Optimize mode, in other modes like Scan/Explore etc, it will return or use only the default value.

If you are using optimize mode, then where does the need for using a loop arise, the optimizer runs the code once for each value.
If there are more than 1 optimize variables, then you will have a permutation of each one.

All the results are displayed in the result list.

Why would you run the loop from I=1 for Buy, is it not redundant to a large extent ?

/// @link https://forum.amibroker.com/t/using-for-loop-to-write-afl/8404/5
// loop invariant code outside of loop
range = H-L;
refATR = Ref(ATR(5),-1);
Buy = 1;
for (n = 1; n <= 3; n++ )
Buy &&= abs(Ref(range,-n)) < refATR;
Sell = Cross(MA(C,50), C);

is doing the same thing as this one (of first post)

Buy= abs(Ref(H,-1)-Ref(L,-1)) < Ref(ATR(5),-1) AND abs(Ref(H,-2)-Ref(L,-2)) < Ref(ATR(5),-1) AND abs(Ref(H,-3)-Ref(L,-3)) < Ref(ATR(5),-1);
Sell = Cross(MA(C,50), C);

Now, as for optimization of number of range max. look-back and in order to get backtest report there you need to set Setoption -> GenerateReport to 1 to get full report for each iteration.

/// @link https://forum.amibroker.com/t/using-for-loop-to-write-afl/8404/5
SetOption("GenerateReport", 1 );// force full report creation in optimization
num_conditions = Optimize("Max. H-L look back", 1, 1, 20, 1);
// loop invariant code outside of loop
range = H-L;
refATR = Ref(ATR(5),-1);
Buy = 1;
for (n = 1; n <= num_conditions; n++ )
Buy &&= abs(Ref(range,-n)) < refATR;
Sell = Cross(MA(C,50), C);