I'm trying to write and reclassification expresion, within the field calculator, that works in two different layers (vectorial) with two different names for ther same thing. The issue here is that in my approach, as one of the attributes names doesn't exist in the layer, the expression doesn't work.
case
when ("layer1colname" = 10 or "layer2colname" = 10) then "CAT10"
end
I am thinking about two different approaches:
- Including a piece of code that first finds if the attribute exist.
- Use other reclassification tool (for vectorial data) out of the field calculator.
-
2Are you reclassifying manually, or is this part of a model?Erik– Erik2020年04月08日 09:53:25 +00:00Commented Apr 8, 2020 at 9:53
-
In fact I'm trying to implement this function within a model, where I'm stack as well in this other question: gis.stackexchange.com/questions/343327/…César Arquero Cabral– César Arquero Cabral2020年04月08日 11:00:16 +00:00Commented Apr 8, 2020 at 11:00
2 Answers 2
You can use the attribute
or attributes
function in your expression to build the logic you want.
The fragment attribute($currentfeature,'layer1colname')
will return the value of that attribute in the current feature, if it exists, and NULL if not as opposed to an error. Ditto attributes()['layer1colname']
. You could then use CASE WHEN
and/or if ... is NULL
to pick out the right one.
Actually, attributes()
alone returns a map of all attributes of the current and/or other specified feature as a map (not cartographic map, a Python map...) with the attribute names as keys. You could use this for fancier logic to parse for relevant attribute names in a more complex manner.
Note in the above the attribute name is in single quotes '...'
since it is a string being passed to the attribute()
function to work with; with the more usual "..."
the expression evaluation engine would try to substitute the value of the attribute before invoking the function.
Finally, my original thought was to use try("Attr1","Attr2")
which in general ought to return its 2nd argument if the 1st one generates an error, but seems to in this case only generate a NULL if "Attr1"
is invalid in the layer.
-
1Thansk a lot. Based on your answer I did a nested try function (TRY(TRY("TIPESTR" , "TIPESTR50" ) , "TIPESTR" ))César Arquero Cabral– César Arquero Cabral2020年04月08日 10:30:02 +00:00Commented Apr 8, 2020 at 10:30
Not a check of if a field exists but to get the calculation to run without causing an error you can use try
:
Tries an expression and returns its value if error-free. If the expression returns an error, an alternative value will be returned when provided otherwise the function will return null.
try((case
when "not_a_field" = 1 then 1
when "LAN_KOD" = 22 then 22
else pass
end), 0)
-
1I like both answers but I decided to give @Houska the answer as He/She pointed sooner in the TRY direction. Thanks a lot. By the way, I finaly did TRY(TRY("TIPESTR" , "TIPESTR50" ) , "TIPESTR" )César Arquero Cabral– César Arquero Cabral2020年04月08日 10:29:10 +00:00Commented Apr 8, 2020 at 10:29