Qlikview - multiple if in script - loops

I have table:
I want to make in script to load data this:
(if((color = 'blue' or color = 'green' or color = 'red') and place = 'A','GROUP A') or
if((color = 'yellow' or color = 'red' or color = 'blue') and place = 'B','GROUP B')) as allPl
but when create list my allPl is empty.
Any idea?

The most simple solution, I think, will be
If(mixmatch(id,'blue','green','red') and place='A','Group A',
If(mixmatch(id,'blue','green','yellow') and place='B','Group B')) as allPl

You need to nest the if statements to get the result.
if( condition1 = true, result1,
if(condition2 = true <at this point condition1 = false>, result2 ...
For your case:
if( color = 'blue'
or color = 'green'
or color = 'red','GROUP A',
if( color = 'yellow'
or color = 'red'
or color = 'blue','GROUP B')
) as allPl
The script above will produce the following result:
But i'm not sure that this is the result you want. As you can see from the image above only the yellow value will have GROUP B assigned using this approach.
Leave a comment is this is the case

You can also use this solution.
map_allPl:
mapping
load
color & '##separator##' & place AS IN
,allPl AS OUT
inline
[color,place,allPl
blue,A,GROUP A
green,A,GROUP A
red,A,GROUP A
yellow,B,GROUP B
red,B,GROUP B
blue,B,GROUP B];
table:
load
*
,applyMap('map_allPl',color & '##separator##' & place,'nd') AS allPl
inline
[id,color,place
1,blue,A
2,green,A
3,red,A
4,yellow,B
5,red,B
6,blue,B
];

you can try with match() or wildmatch() or mixmatch() to reduce your expression.
try like,
if(match(color,'blue','green','red') and place='A','Group A',
if(match(color,'yellow','red','blue') and place='B','Group B')
) as appPl
Regards,

Related

How can I use my plotted data in further calculations?

So I have this code that draws zigzag-alike line
indicator("Custom zigzag", overlay=true)
bullish(at) => open[at] < close[at]
bearish(at) => open[at] > close[at]
break_up() =>
if close != open
at = 1
while close[at] == open[at]
at += 1
if bearish(at) and bullish(0)
true
else
false
else
false
break_down() =>
if close != open
at = 1
while close[at] == open[at]
at += 1
if bearish(0) and bullish(at)
true
else
false
else
false
u = break_up()
d = break_down()
plot(u?open[0] : d?open[0] : na, color = color.fuchsia, linewidth = 1, style = plot.style_line, offset=0)
I want to use the result in some further calculations, but I dont get it, how can I put the whole u?open[0] : d?open[0] : na in an array?
Roughly pushing values to an array variable leads to recalculation on each bar, IMO.
Or can I access somehow my own previous plot, since custom script call is not possible?
There are two ways to do it depending on do you want na values as it is or previous calculated values in place of na. You can save the whole thing in a variable and then use that to calculate anything like sma etc. First way
//Keeping na value
val=u?open[0] : d?open[0] : na
s=ta.sma(val,10)
plot(s)
Second way
//Replacing na values with previous values
var val=open[0]
val:=u?open[0] : d?open[0] : val[1]
s=ta.sma(val,10)
plot(s)

How can I slide over values from specific columns to specific columns within the same dataset?

I have a post-joined datasets where the columns are identical except the right side has new and corrected data and a .TODROP suffix appended at the end of the column's name.
So the dataset looks something like this:
df = spark.createDataFrame(
[
(1, "Mary", 133, "Pizza", "Mary", 13, "Pizza"),
(2, "Jimmy", 8, "Hamburger", None, None, None),
(3, None, None, None, "Carl", 6, "Cake")
],
["guid", "name", "age", "fav_food", "name.TODROP", "age.TODROP", "fav_food.TODROP"]
)
I'm trying to slide over the right side columns to the left side columns if there is value:
if df['name.TODROP'].isNotNull():
df['name'] = df['name.TODROP']
if df['age.TODROP'].isNotNull():
df['age'] = df['age.TODROP']
if df['fav_food.TODROP'].isNotNull():
df['fav_food'] = df['fav_food.TODROP']
However, the problem is that the brute-force solution will take a lot longer with my real dataset because it has a lot more columns than this example. And I'm also getting this error so it wasn't working out anyway...
"pyspark.sql.utils.AnalysisException: Can't extract value from
name#1527: need struct type but got string;"
Another attempt where I try to do it in a loop:
col_list = []
suffix = ".TODROP"
for x in df.columns:
if x.endswith(suffix) == False:
col_list.append(x)
for x in col_list:
df[x] = df[x + suffix]
Same error as above.
Goal:
Can someone point me in the right direction? Thank you.
First of all, your dot representation of the column name makes confusion for the struct type of column. Be aware that. I have concatenate the column name with backtick and it prevents the misleading column type.
suffix = '.TODROP'
cols1 = list(filter(lambda c: not(c.endswith(suffix)), df.columns))
cols2 = list(filter(lambda c: c.endswith(suffix), df.columns))
for c in cols1[1:]:
df = df.withColumn(c, f.coalesce(f.col(c), f.col('`' + c + suffix + '`')))
df = df.drop(*cols2)
df.show()
+----+-----+---+---------+
|guid| name|age| fav_food|
+----+-----+---+---------+
| 1| Mary|133| Pizza|
| 2|Jimmy| 8|Hamburger|
| 3| Carl| 6| Cake|
+----+-----+---+---------+

BackgroundColor expression

I created a Base_Rent_Variance Calculated field that works like it should:
=IIF(Fields!CurrNrmRent.Value = 0 and Fields!PriorNrmRent.Value > 0, "Review", IIF(Fields!PriorNrmRent.Value = 0 and Fields!CurrNrmRent.Value > 0, "Review", IIF(Fields!CurrNrmRent.Value > 0 and Fields!PriorNrmRent.Value > 0, (Fields!CurrNrmRent.Value-Fields!PriorNrmRent.Value)/IIF(Fields!PriorNrmRent.Value = 0, 1, Fields!PriorNrmRent.Value), nothing)))
I am trying to create a BackgroundColor expression so that if Base_Rent_Variance >= 15% or <= -15%, the background color is red, and if it equals Review the color is red. The expression I created is filling the background red correctly for the 15% variances but not the Review. My expression is below. What am I doing wrong?
=IIF(Fields!Base_Rent_Variance.Value >= .15 or Fields!Base_Rent_Variance.Value <= -.15, "Red",iif(RTRIM(Fields!Base_Rent_Variance.Value) = "Review","Red","White"))
This is likely an issue with your datatypes. You're attempting to store both numeric and string types in the same field. I would use a conversion to be sure you have the correct datatypes. This expression should handle the mismatched datatypes.
=IIF(CDbl(Fields!Base_Rent_Variance.Value) >= .15 or CDbl(Fields!Base_Rent_Variance.Value) <= -.15,
"Red",
IIF(TRIM(CStr(Fields!Base_Rent_Variance.Value)) = "Review","Red","White"))
Another option to try is using the InStr function like the following.
=IIF(CDbl(Fields!Base_Rent_Variance.Value) >= .15 or CDbl(Fields!Base_Rent_Variance.Value) <= -.15,
"Red",
IIF(InStr(CStr(Fields!Base_Rent_Variance.Value), "Review"),"Red","White"))
Based on the comment below, let's try this one with a switch statement. The following switch statement will evaluate the first expression, set the cell red if true, check the second expression, set the cell red if true, and finally set anything left to white.
=SWITCH(CDbl(Fields!Base_Rent_Variance.Value) >= .15 or CDbl(Fields!Base_Rent_Variance.Value) <= -.15, "Red",
InStr(CStr(Fields!Base_Rent_Variance.Value), "Review"),"Red",
true, "White")
You can also use me.Value in colour expressions.
For example:
=iif(me.Value = "Review" OrElse me.Value >= 0.15 OrElse me.Value <= -0.15, "Red", "NoColor")
This means you don't have to recalculate your values each time, or keep track of changes in several locations if the calculations change.

Shiny assign reactive variable from input using loop

I'm trying to assign reactive variable based on my input using loop. For example, I want to select the column (from input) in iris data set. Then get the unique value from that column. And I want to do this in the loop. I find it works for my 'joke' variable, but not for my 'Group[[paste0('Gcol',i)]]' variable. I've been searching answer for this for days.
Thank you for your help in advance!
library(shiny)
data=iris
ui <- fluidPage(
titlePanel("Old Faithful Geyser Data"),
sidebarLayout(
sidebarPanel(
fluidRow(
column(9,wellPanel(lapply(1:5, function(i) {
selectizeInput(paste0('GroupVar',i), paste0('Group ',i), choices = sort(colnames(data)),
options = list(placeholder = 'Select one',
onInitialize = I('function() {
this.setValue(""); }')))
})
)))
),
mainPanel(
fluidRow(column(6, wellPanel(
lapply(1:5, function(i) {
uiOutput(paste0('GroupOpt', i))
})
))),
textOutput("try4"),
textOutput("try2"),
textOutput("try21"),
textOutput("try3"),
textOutput("try")
)
)
)
server <- function(input, output) {
Group=reactiveValues()
for (i in 1:5){
Group[[paste0('Gcol',i)]]=reactive({
data[,which(colnames(data)==
input[[paste0('GroupVar',i)]])]})
}
joke=reactive({data[,which(colnames(data)==input[[paste0('GroupVar',1)]])]})
lapply(1:5, function(i) { output[[paste0('GroupOpt',i)]] = renderUI({
selectInput(paste0("GroupOpt",i), "Select group",multiple=TRUE,
sort(as.character(unique(Group[[paste0('Gcol',i)]])))
)
})})
output$try4 = renderText({print(paste0('it
is',input[[paste0('GroupVar',1)]]))})
output$try2 = renderText({print(dim( Group[[paste0('Gcol',1)]]()))})
output$try21 = renderText({print(class( Group[[paste0('Gcol',1)]]()))})
output$try3 =
renderText({print(which(colnames(data)==input[[paste0('GroupVar',1)]]))})
output$try = renderText({print(unique(as.character(joke())))})
}
# Run the application
shinyApp(ui = ui, server = server)
data[, which(colnames(data)=="Species")] is not a dataframe, this is the column Species, a factor. If you want to allow a one-column dataframe, do data[, which(colnames(data)=="Species"), drop=FALSE]
Replace your loop with the following one, and your app works (but maybe not as you expect; I'm not sure to understand what you want).
for (i in 1:5){
local({
ii <- i
Group[[paste0('Gcol',ii)]]=reactive({
data[,which(colnames(data)==input[[paste0('GroupVar',ii)]])]})
})
}

find and replace symbol using vbs

I am working a 1XXX words documents, I want to use vbs to changing the status of checkbox faster but I can't found any work solution, after that, i wonder if find and replace can solve my issue, so i wrote some code for this
Const wdReplaceAll = 2
Set objWord = CreateObject("Word.Application")
objWord.Visible = True
Set objDoc = objWord.Documents.Open("C:\checkbox.doc")
Set objDoc = objWord.Documents.Add()
Set objSelection = objWord.Selection
objSelection.Find.Text = "#1"
objSelection.Find.Forward = TRUE
objSelection.Find.MatchWholeWord = TRUE
objSelection.Find.Replacement.Text = objSelection.InsertSymbol 253, "Wingdings"
objSelection.Find.Execute ,,,,,,,,,,wdReplaceAll
But, it can't work, and always show the error on the objSelection.InsertSymbol 253...
You can't use InsertSymbol in an assignment like that. Either replace the search text with an appropriate character formatted as "Wingdings":
With objSelection.Find
.Text = "#1"
.Replacement.Text = ChrW(61693)
.Replacement.Font.Name = "Wingdings"
...
End With
objSelection.Find.Execute ,,,,,,,,,,wdReplaceAll
or just Find the search text and then use InsertSymbol on the selection:
objSelection.Find.Text = "#1"
objSelection.Find.Execute
objSelection.InsertSymbol 253, "Wingdings"

Resources