Compare and divide in report builder - sql-server

I have a condition I want to divide two values in report builder with same date but different sample name in the same table...
For example, in this image, I want to divide the CM2(2.85) and Raw Meal(0.58) value. their result should be 4.9.
And if these two parameters (CM2 and Raw Meal) are not on the same date then the value should be empty or nothing. Please help I am new to report builder expression.
I've tried this expression but it does not give me what I need
IIf(InStr(Fields!Sample_Code.Value,"CM2") > 0, Fields!So3.Value, nothing) / IIf(InStr(Fields!Sample_Code.Value,"Raw Meal") > 0, Fields!So3.Value, nothing)

The record will either be CM2 or Raw Meal, but it will never contain both at the same time. If Fields!Sample_Code.Value = "CM2" is true, the second half of the expression will be false, or vice-versa. Fields!Sample_Code.Value can't be two different values at the same time, it can only contain the data from a single record.
Your expression will result in either:
nothing/Fields!So3.Value
or
Fields!So3.Value/nothing.
As a simplified example:
IF( x=1 , 1 , null) / IF( x=2 , 1 , null)
X cannot be two different values at the same time so the expression will never return a non-null result.
You'll need to join CM2 and RAW MEAL records together to evaluate them at the same time. That would probably require a significant change to what you've posted so far.

Related

What is wrong with this expressions? =CountRows(ReportItems!Textbox58.Value = "Intervene"). I want to count each row which says Intervene

What is wrong with this expression? =CountRows(ReportItems!Textbox58.Value = "Intervene")
I want to count each row which says Intervene.
As Larnu has commented, you cannot use CountRows against the ReportItems collection.
Probably what you need to do is
Look at the expression in Textbox58 and see where it gets it's data from. In this exmaple let's say it comes from Fields!myFieldName.Value.
Now we need to count the rows where Fields!myFieldName.Value = "Intervene" but rather than using count, we can convert these matches to return 1 or 0 where the field is not "Intervene"
So the expression would look something like this
=SUM(IIF(Fields!myFieldName.Value = "Intervene", 1, 0))
This will sum the rows withing the current scope, so if this is contained in a row group for example, then it will only sum those rows in that row group.
If you need to count based on a a different scope (e.g. the entire dataset) then you can specify that in the SUM() function like this
=SUM(IIF(Fields!myFieldName.Value = "Intervene", 1, 0), "DataSet1")
Here we are summing across the entire dataset where the dataset name is DataSet1
Update based on OP comment
As your expression is
=SUM(IIF(Fields!Actual_Duration.Value >= 10, "Intervene", "No Intervention Needed"))
What we actually need to count is instances where Actual_Duration is >= 10.
So the final expression should be
=SUM(IIF(Fields!Actual_Duration.Value >= 10, 1, 0))

Column in SSRS to show value according to the parameter value in SSRS

I have one column in SSRS report which should show the value according to the parameter, if the parameter is selected to Million Euro then it should show the value in Million Euro which means the value should be divided by 10^6,if the parameter is selected as K Euro then the value should be as K Euros which means the value should be divided by 10^3.
I tried to create a dataset where I wrote the SQL query and made a parameter but it didn't worked.
Can anyone give the solution like what should be my dataset query and how should I map it with the parameter.
I used
if #CurrencyConv='MEuro' BEGIN
select 1/Power(10,6) as ProductValue
end
else BEGIN select 1/Power(10,3) as ProductValue
END
And made a parameter where I hardcoded the available values as 'MEuro' and 'KEuro'
And in that column's expression I multiplied the column value with Dataset Value(ProductValue)
Column name is Converted Booking and I have to multiply that column according to the parameter value so if the value is MEuro then it should be [Converted Booking]*1/Power(10,6)
In Sql the below query is working
select [Converted Booking]*1/Power(10,6) from T_GCP_REP
How to apply same thing in SSRS
If you want the final calculated value in you dataset then change your dataset query to
SELECT
*,
CAST([Converted Booking] as float) / CASE WHEN #CurrencyConv = 'MEuro' THEN 1000000 ELSE 1000 END as ConvertedBookingFinal
from T_GCP_REP
OR
If you want to do this purely in SSRS (maybe you cannot change your dataset query?)
The Set the parameter values to 1000 and 1000000 respectively.
Then in the report textbox set the expression to
= Fields.Converted_Booking.Value / Parameters!myParameterName.Value
you can leave the parameter labels as "MEuro" etc you only need to change the value.
If you want the field in your SQL, you can add it using a CASE statement.
SELECT *, 1/Power(10, CASE WHEN #CurrencyConv = 'MEuro' THEN 6 ELSE 3 END) as ProductValue
FROM TABLE
or you could use the new IIF in SQL like SSRS has
SELECT *, 1/Power(10, IIF(#CurrencyConv = 'MEuro', 6, 3)) as ProductValue
FROM TABLE
For an SSRS expression, an IIF statement could also be used:
=1/Power(10, IIF(Parameters!CurrencyConv.Value = 'MEuro', 6, 3))
Though it might be better to use MEuro as the parameter label and have 6 as the value (with KEuro, 3 for the other possible value). Then you could shorten it to:
=1/Power(10, Parameters!CurrencyConv.Value)

Inserting rows to dataframe on multiple indices based on conditions in python-pandas

I have a dataframe like this
Whenever I see an instance where start is followed by stop and DURATION column is 0, I need to insert a row after that (at 4th and 8th row in this case), which should contain pretty much the same values of its previous row, but the event column should be denoted by E1.
I need to get something like this
How can I achieve this since multiple indices can have the values with START-STOP and duration as 0?
Thanks in advance!
If you always have a sequence 'start-stop' (stop is always followed by start), it will work:
df.loc[(df['DURATION'] == 0) & (df['event'] == 'stop'), 'event'] = 'E1'
What means: Put 'E1' in column 'event' for each row which has 0 in column 'DURATION' and 'stop' in column 'event'.

MATLAB Extract all rows between two variables with a threshold

I have a cell array called BodyData in MATLAB that has around 139 columns and 3500 odd rows of skeletal tracking data.
I need to extract all rows between two string values (these are timestamps when an event happened) that I have
e.g.
BodyData{}=
Column 1 2 3
'10:15:15.332' 'BASE05' ...
...
'10:17:33:230' 'BASE05' ...
The two timestamps should match a value in the array but might also be within a few ms of those in the array e.g.
TimeStamp1 = '10:15:15.560'
TimeStamp2 = '10:17:33.233'
I have several questions!
How can I return an array for all the data between the two string values plus or minus a small threshold of say .100ms?
Also can I also add another condition to say that all str values in column2 must also be the same, otherwise ignore? For example, only return the timestamps between A and B only if 'BASE02'
Many thanks,
The best approach to the first part of your problem is probably to change from strings to numeric date values. In Matlab this can be done quite painlessly with datenum.
For the second part you can just use logical indexing... this is were you put a condition (i.e. that second columns is BASE02) within the indexing expression.
A self-contained example:
% some example data:
BodyData = {'10:15:15.332', 'BASE05', 'foo';...
'10:15:16.332', 'BASE02', 'bar';...
'10:15:17.332', 'BASE05', 'foo';...
'10:15:18.332', 'BASE02', 'foo';...
'10:15:19.332', 'BASE05', 'bar'};
% create column vector of numeric times, and define start/end times
dateValues = datenum(BodyData(:, 1), 'HH:MM:SS.FFF');
startTime = datenum('10:15:16.100', 'HH:MM:SS.FFF');
endTime = datenum('10:15:18.500', 'HH:MM:SS.FFF');
% select data in range, and where second column is 'BASE02'
BodyData(dateValues > startTime & dateValues < endTime & strcmp(BodyData(:, 2), 'BASE02'), :)
Returns:
ans =
'10:15:16.332' 'BASE02' 'bar'
'10:15:18.332' 'BASE02' 'foo'
References: datenum manual page, matlab help page on logical indexing.

Link two tables based on conditions in matlab

I am using matlab to prepare my dataset in order to run it in certain data mining models and I am facing an issue with linking the data between two of my tables.
So, I have two tables, A and B, which contain sequential recordings of certain values in a certain timestamps and I want to create a third table, C, in which I will add columns of both A and B in the same rows according to some conditions.
Tables A and B don't have the same amount of rows (A has more measurements) but they both have two columns:
1st column: time of the recording (hh:mm:ss) and
2nd column: recorded value in that time
Columns of A and B are going to be added in table C when all the following conditions stand:
The time difference between A and B is more than 3 sec but less than 5 sec
The recorded value of A is the 40% - 50% of the recorded value of B.
Any help would be greatly appreciated.
For the first condition you need something like [row,col,val]=find((A(:,1)-B(:,1))>2sec && (A(:,1)-B(:,1))<5sec) where you do need to use datenum or equivalent to transform your timestamps. For the second condition this works the same, use [row,col,val]=find(A(:,2)>0.4*B(:,2) && A(:,2)<0.5*B(:,2)
datenum allows you to transform your arrays, so do that first:
A(:,1) = datenum(A(:,1));
B(:,1) = datenum(B(:,1));
you might need to check the documentation on datenum, regarding the format your string is in.
time1 = [datenum([0 0 0 0 0 3]) datenum([0 0 0 0 0 3])];
creates the datenums for 3 and 5 seconds. All combined:
A(:,1) = datenum(A(:,1));
B(:,1) = datenum(B(:,1));
time1 = [datenum([0 0 0 0 0 3]) datenum([0 0 0 0 0 3])];
[row1,col1,val1]=find((A(:,1)-B(:,1))>time1(1)&& (A(:,1)-B(:,1))<time1(2));
[row2,col2,val2]=find(A(:,2)>0.4*B(:,2) && A(:,2)<0.5*B(:,2);
The variables of row and col you might not need when you want only the values though. val1 contains the values of condition 1, val2 of condition 2. If you want both conditions to be valid at the same time, use both in the find command:
[row3,col3,val3]=find((A(:,1)-B(:,1))>time1(1)&& ...
(A(:,1)-B(:,1))<time1(2) && A(:,2)>0.4*B(:,2)...
&& A(:,2)<0.5*B(:,2);
The actual adding of your two arrays based on the conditions:
C = A(row3,2)+B(row3,2);
Thank you for your response and help! However for the time I followed a different approach by converting hh:mm:ss to seconds that will make the comparison easier later on:
dv1 = datevec(A, 'dd.mm.yyyy HH:MM:SS.FFF ');
secs = [3600,60,1];
dv1(:,6) = floor(dv1(:,6));
timestamp = dv1(:,4:6)*secs.';
Now I am working on combining both time and weight conditions in a piece of code that will run. Should I use an if condition inside a for loop or is a for loop not necessary?

Resources