variable being shadowed in trading view pinescript, saying use := instead - if-statement

I am new to pinescript and have coded a simple indicator in trading view pinescript. I can get my buy and sell labels and also send alert when conditions are met.
I am trying to store the entry price as a variable when a sell or buy signal has been met. I also pass a var called pos which is 1 for sell and 2 for long.
i am trying to make the indicator send an alert when the entry price is above or below 20 pips. however my variable which is passed to the alert is being shadowed??? why??? im sure my code is correct?
var pos=0
var short_update = false
var entry_price = 0
if sellSignal
longLabel = label.new(
x=bar_index,
y=na,
text="Sell - "+ str.tostring(RoundUp(hlc3,2)),
xloc=xloc.bar_index,
yloc=yloc.abovebar,
color=color.red,
textcolor=color.white,
style=label.style_label_down,
size=size.normal)
entry_price=close
pos=1
alertcondition(sellSignal, "Short Alert", "Go short")
price_lower=entry_price-20
current_price=close
if pos==1 and current_price < price_lower
short_update=true
alertcondition(short_update, "Move Stop at BE", "BE")
above is my attempt at coding an alert condition if the entry price of a short is now 20 pips less...not working? please help

Actually all your variables defined with var on top are being shadowed not only "the one" you're referring to.
Shadowing variable 'pos' which exists in parent scope. Did you want to
use the ':=' operator instead of '=' ?
What does it mean?
You have declared your variables and assigned the first values correctly by the assignment operator: = in the global scope. If you want to update these values later on you'll need the reassignment operator though: :=.
The := is used to reassign a value to an existing variable. It says
use this variable that was declared earlier in my script, and give it
a new value.
source
So in your case var pos=0, var short_update = false, var entry_price = 0 are not getting updated through your whole script, are jut being redeclared as new variables in your local scopes that have no effect on the global ones, though having the same name.The solution is as simple as the error message says: use := instead of = if you want to update a declared variable.
Final note: try updating eg.: pos like this pos=1 in the global scope below you var pos=0 declaration. You'll get an error saying "'pos' is already defined". The same applies to your example, the only difference is that it is not illegal to redeclare a variable in a local scope, but Pine Script warns you correctly that it's probably not what you wanted.

Related

Why do I get an invalid syntax error with a foreach loop?

I want to rename variable names starting with intensity. I received an invalid syntax, r(198) error, with the following code.
#delimit;
foreach VAR of varlist intensity* {;
local NEW = subinstr("`VAR'", "intensity", "int");
rename `VAR' `NEW';
};
Your use of the delimiter ; here does not bite, so I will ignore it.
The error is in the use of subinstr(), which must have four arguments, the fourth being the number of substitutions to be made. See help subinstr().
This works (note please the use of a minimal complete verifiable example):
clear
set obs 1
generate intensity1 = 1
generate intensity2 = 2
foreach VAR of varlist intensity* {
local NEW = subinstr("`VAR'", "intensity", "int", 1)
rename `VAR' `NEW'
}
ds
But the loop is utterly unnecessary. First, let's flip the names back and then show how to change names directly:
rename int* intensity*
rename intensity* int*
See help rename groups for more.

Error - Cannot assign to value: function call returns immutable value

I'm doing an introductory iOS developer's course, and am doing a cat-years calculator as an exercise. The following code returns the error:
Int(AgeInCatYears.text!) = CatsROld!
Error - Cannot assign to value: function call returns immutable value
In case it's important, the var CatsROld was set equal to Int(humanYears.text!)! * 7 one line earlier.
Any advice?
If you are setting value to the Label or textField then you need to simply set value (as String) to its property text, but you are try to convert the value to Int and then you assigning value of CatsROld to it, that is the reason you are getting this error. So simply write like AgeInCatYears.text = "\(CatsROld!)"
AgeInCatYears.text = "\(CatsROld!)"
Note: You are force wrapping CatsROld value with !, if you are 100% sure that it will not nil then its ok other wise you need to use if let or guard for optional wrapping.

GoogleSheet script editor - onEdit event with conditions / if statement

guys!
I'm new to this website and also not good with coding. So I would really appreciate some help.
Right now I'm in need of a specific code to make a google sheet work perfectly.
To further explain:
I have a google sheet that a few information will be input by other co-workers. What I need is a code that will register the date in a specific cell and by whom the input was made on another cell.
So far this is what I have:
function onEdit(event) {
var sheet = event.source.getSheetByName("Input");
// Note: actRng = return the last cell of the row modified
var actRng = event.source.getActiveRange();
var index = actRng.getRowIndex();
var cindex = actRng.getColumnIndex();
// Note: date = return date
// Note: user = return the user email
var userCell = sheet.getRange(index,14);
var dateCell = sheet.getRange(index,2);
var inputdate = Utilities.formatDate(new Date(), "GMT+0200", "yyyy-MM-dd");
// Note(with hour): var inputdate = Utilities.formatDate(new Date(), "GMT+0200", "yy-MM-dd HH:mm");
//var user = event.user; // Note: event.user will not give you collaborator's Id
var user = Session.getEffectiveUser();
// Note: setValue = Insert in the cell the date when this row was modified
if (userCell.Value == null) {
userCell.setValue(user);
dateCell.setValue(inputdate)
}
}
My main problems/questions are:
I don't exactly need the last modifier, but the person who first input info on the cells. Therefore I tried that last IF (If the cell that is supposed to have the last modifier e-mail is blank, it means that nobody changed that row before, so the code should add the user on the userCell), although it is not working since every change I make it ignores the verification.
I also want to add that the event will only happen if you add values, if you delete them, nothing happens. (so far even when I delete cells, it counts as modification)
Most of the sheet is protected to avoid that people by accident erase some of the formulas, so the cells that this code changes are also protected. Is there a way to make the code bypass cell protection?
Please, help me identify what I'm doing wrong and hopefully I'll get this working perfectly! Thanks for the help !
If you want to prevent the script from firing when a cell is deleted, try:
var editedCell = SpreadsheetApp.getActiveSheet().getRange(e.range.getRow(), e.range.getColumn());
if (editedCell == "") {
return;
}
I would change Session.getEffectiveUser() to session.getActiveUser().
The last if statement is unnecessary. You want whoever most recently edited the field to be identified, along with the date.

giving a string variable values conditional on another variable

I am using Stata 14. I have US states and corresponding regions as integer.
I want create a string variable that represents the region for each observation.
Currently my code is
gen div_name = "A"
replace div_name = "New England" if div_no == 1
replace div_name = "Middle Atlantic" if div_no == 2
.
.
replace div_name = "Pacific" if div_no == 9
..so it is a really long code.
I was wondering if there is a shorter way to do this where I can automate assigning values rather than manually hard coding them.
You can define value labels in one line with label define and then use decode to create the string variable. See the help for those commands.
If the correspondence was defined in a separate dataset you could use merge. See e.g. this FAQ
There can't be a short-cut here other than typing all the names at some point or exploiting the fact that someone else typed them earlier into a file.
With nine or so labels, typing them yourself is quickest.
Note that you type one statement more than you need, even doing it the long way, as you could start
gen div_name = "New England" if div_no == 1

Can you var scope multiple variables at once in Coldfusion?

While it is possible and does not throw an error I would like to know if it's an approved practice to var scope multiple variables in one line like this:
<cfset VAR var1 = var2 = var3 = ''>
I would appreciate all ideas and opinions especially if they come with documentation as a supporting argument. I know that it works without throwing an error but I can't find specific documentation saying whether it will scope a variable or if it just declares the value.
Thanks!
FWIW, yes, you can do this in CF9:
<cfset var a = var b = c = d*5>
Here's the documentation which gives that example. In this case I'm assuming variables c and d were already defined earlier in the function.
So you need to repeat the var keyword for each variable, and in your case this would result in:
<cfset VAR var1 = VAR var2 = VAR var3 = ''>
As everyone said you need to scope your variables with var or local. Also as #Ben said, you can't really var scope variables like you have. What I would suggest is use the local scope and do something like the following:
<cfscript>
var val = 'some value'
local = {
var1 = duplicate(val),
var2 = duplicate(val),
var3 = duplicate(val)
};
</cfscript>
That, in my opinion, is the fastest way to achieve what you seem to be doing. I use the duplicate function just so if you use a complex variable as the value of val (struct, array, etc) you don't run into issue with references.
<cfset> does not scope variables.
To properly scope the variables requires the var keyword
<cfset var someVariable = 1>
Otherwise the variables will be created, but assigned to the default scope.
The default scope depends on the context and what version of CF we are talking about.
For CFC methods:
CF9 -> LOCAL scope
CF8 -> VARIABLES scope
Because of the scoping rules in CF9 the var keyword is not really needed.
Variables can be added to the LOCAL scope directly and at any time (<cfset LOCAL.foo = "bar"). There is no need scope them ahead of time.
I suppose I should start by pointing out that your code doesn't var scope the variables, it just sets their values. You need to use the VAR keyword (or LOCAL scope in CF9) to specify that the variables should be VAR scoped.
Furthermore, chaining assignments doesn't work in all versions of CF. My workplace is still on 6.1, and this throws an error.
Finally, if I recall correctly, if you use the assignment statement as above, var1 and var2 are equal to true, as the result of an assignment operation is true if no error occurred. (someone correct me if I'm wrong, since I can't test it at work, since we're on 6.1)
Anyway, to get back to your question, I don't chain assignment or scoping ever. First, I think individual assignments are clearer. second, it doesn't work in all versions. So I would suggest that individual assignments would be preferred.
I've seen people simply create a var struct and define your variables as keys for the struct. This way you don't have to use var all the time. E.g.:
<cfset var local = structNew() />
<cfset local.var1 = "" />
<cfset local.var2 = "" />
This is helpful for those who use ColdFusion Server 8 and below and are stuck with the var scope.