Automation Array Formula - if-statement

I need to make a formula that generates the number of the incident in this data
Whenever someone takes an action from consequences tab I should choose the incident and the number of it so if someone took the same incident before and will take it again this will be the 2nd time with a different action and every action has a 180 days expiry which is represented in the expiry column 0 means expired 1 means, not expired
what I need here is to generate the number of incidents automatically when the array formula looks at the name of the employee then it counts the incident if the incident number is equal 2 then it means 2 times same incident so generate 2nd time and if it is equal 3 it means 3 times same incident ETC...
I have tried this array but it counts all the errors without taking the agent as criteria
=ARRAYFORMULA(IF(ROW(A:A)=1,"Number of incidents (Automation)",IF(LEN(A:A)=0,IFERROR(1/0),IF(COUNTIF(B:B,B:B)=0," ",IF(COUNTIF(C:C,C:C)=6,"6th Time",IF(COUNTIF(C:C,C:C)=5,"5th Time",IF(COUNTIF(C:C,C:C)=4,"4th Time",IF(COUNTIF(C:C,C:C)=3,"3rd Time",IF(COUNTIF(C:C,C:C)=2,"2nd Time",IF(COUNTIF(C:C,C:C)=1,"1st Time"," "))))))))))
here is a sample of the data https://docs.google.com/spreadsheets/d/1OqxTwyeZlbzYsUYIF6sNqkQS3uzEkpyC15RRVP2P4rA/edit?usp=sharing

try like this in D1:
={"Number of incidents (Automation)";
ARRAYFORMULA(IF(LEN(C2:C), COUNTIFS(C2:C, C2:C, ROW(C2:C), "<="&ROW(C2:C)), ))}
if that needs to be per employee then use:
={"Number of incidents (Automation)";
ARRAYFORMULA(IF(LEN(C2:C), COUNTIFS(B2:B&C2:C, B2:B&C2:C, ROW(C2:C), "<="&ROW(C2:C)), ))}
and to exclude expired you can do:
={"Number of incidents (Automation)";
ARRAYFORMULA(IF(F2:F=1, COUNTIFS(B2:B&C2:C&F2:F, B2:B&C2:C&F2:F, ROW(C2:C), "<="&ROW(C2:C)), ))}

I didn't get what you exactly want. But hope this helps you.
Instead of
IF(COUNTIF(C:C,C:C)=X,"Xnd Time"
You can write
IF(COUNTIF(C:C,C:C)&"nd Time"
in full formula
=ARRAYFORMULA(IF(ROW(A:A)=1,"Number of incidents (Automation)",IF(LEN(A:A)=0,IFERROR(1/0),IF(COUNTIF(B:B,B:B)=0," ",COUNTIF(C:C,C:C)&"th Time"))))

Related

Simplify google sheet formula "SUM / INDEX / MATCH"

I am trying to use google sheet to create a roster formula, to sum up the duty hour per week using INDEX/MATCH/SUM.
But it's too long, is there any way to simplify the formula?
Also, I realize "MATCH" cannot recognize blank cell (N20), can that be fixed too?
=IFERROR(SUM(INDEX($O$12:$O$20,MATCH(D17,$N$12:$N$20,0)),INDEX($O$12:$O$20,MATCH(E17,$N$12:$N$20,0)),INDEX($O$12:$O$20,AND(F17,$N$12:$N$20,0)),INDEX($O$12:$O$20,MATCH(G17,$N$12:$N$20,0)),INDEX($O$12:$O$20,MATCH(H17,$N$12:$N$20,0)),INDEX($O$12:$O$20,MATCH(I17,$N$12:$N$20,0)),INDEX($O$12:$O$20,MATCH(J17,$N$12:$N$20,0))),"Err")
try:
=ARRAYFORMULA(MMULT(IFERROR(REGEXREPLACE(UPPER(B6:H14), "^"&TEXTJOIN("$|^", 1, L1:L10)&"$",
VLOOKUP(REGEXEXTRACT(UPPER(B6:H14), "^"&TEXTJOIN("$|^", 1, L1:L10)&"$"), L1:M10, 2*
SIGN(ROW(A6:A14)), 0)&""), UPPER(B6:H14))*1, TRANSPOSE(COLUMN(B:H))^0))
Franco, since your post says your end goal is to "sum up the duty hour per week," I take that to mean all you need in the end is a single number.
Try this (which will give you total hours for your block that runs B6:H22:
=ArrayFormula(SUM(COUNTIF(B6:H22,$L$1:$L$8)*$M$1:$M$8))
If you need to see the breakdown per code, you can use this:
=ArrayFormula({$L$1:$L$8,COUNTIF(B6:H22,$L$1:$L$8)*$M$1:$M$8})
Just replace "B6:H22" with the reference of each calendar block to get the sum or the breakdown for other weeks.

How to countif 56 exists in 156/56/2567 and only return true once? Google sheets

I have one sheet with data on my facebook ads. I have another sheet with data on the products in my store. I'm having trouble with some countifs where I'm counting how many times my product ID exists in a row where multiple numbers are. They are formatted like this: /2032/2034/2040/1/
It's easy on the rows where only one product ID exists but some rows have multiple ID's separated by a /. And I need to see if the ID exists as a exact match alone or somewhere between the /'s.
Rows with facebook ads data:
A1: /2032/2034/2040/1/
A2: /1548/84/2154/2001/
A3: /2032/1689/1840/2548/
Row with product data:
B1: 2034
C1: I need a countifs here that checks how many times B1 exists in column A. Lets say I have thousands of rows with different variations of A1 where B1 could standalone. How do I count this? I always need exact matches.
You can compare the number you want (56) with the REGEX #MonkeyZeus commented whith a little change -> "(?:^|/)"&B1&"(?:/|$)" so the end result is:
=IF(REGEXMATCH(A1, "(?:^|/)"&B1&"(?:/|$)"), true, false)
Example:
UPDATE
If you need to count the total of 56 in X rows you can change the "True / False" of the condition for "1 / 0" and then do a =SUM(C1:C5) on the last row:
=IF(REGEXMATCH(A1, "(?:^|/)"&B1&"(?:/|$)"), 1, 0)
UPDATE 2
Thanks for contributing. Unfortunately I'm not able to do it this way
since I have loads of data to do this on. Is there a way to do it with
a countif in a single cell without adding a extra step with "sum"?
In that case you can do:
=COUNTA(FILTER(A:A, REGEXMATCH(A:A, "(?:^|/)"&B2&"(?:/|$)")))
Example:
UPDATE 3
With the following condition you check every single possibility just by adding another COUNTIF:
=COUNTIF(A:A,B1) + COUNTIF(A:A, "*/"&B1) + COUNTIF(A:A, B1&"/*") + COUNTIF(A:A, "*/"&B1&"/*")
Hope this helps!
try:
=COUNTIF(SPLIT(A1, "/"), B1)
UPDATE:
=ARRAYFORMULA(IF(A2<>"", {
SUM(IF((REGEXMATCH(""&DATA!C:C, ""&A2))*(DATA!B:B="carousel"), 1, )),
SUM(IF((REGEXMATCH(""&DATA!C:C, ""&A2))*(DATA!B:B="imagepost"), 1, ))}, ))

IF AND OR SWITCH in Google Sheets

I have made a basic formula which calculates the number of staff required to process sales in any given hour on a typical working day.
Now I am trying to create a formula in Google sheets which checks the number of staff required to process the sales VS the actual number of staff who have been rostered on.
I have one row with the predicted hourly sales, one row with the number of staff required to process the sales, and one row with the actual number of staff rostered for every given hour.
I need to create a formula which checks the number of staff required vs the number of staff actually rostered:
IF there is insufficient staff, it will return "Insufficient".
IF the number of staff rostered is sufficient (within 10% less of, or 25% more of the predicted sales), return "Sufficient".
IF there is more than 25% more staff than necessary, return "Overstaffed".
I've searched this, but I am unable to find a suitable example / wrap my head around them and customize them to suit my needs.
I've got reasonable experience programming with PHP, Python, Java, and JavaScript, however, in this instance, I am strictly limited (by my employer) to creating a roster in Google sheets.
I have tried the following:
=IF(F13 = "", "", IF(F15 = "", "", IF(F15 < F13, "Understaffed", IF(F15 >= F13, "Enough Staff", ELSEIF(F15 > (F13*1.3), "Too many staff")))))
And I have also tried:
=SWITCH(G15, G15 < G13, "Under", G15 >= G13, "Fine", G15 > G13*1.3, "Over")
But they do not work correctly.
Can someone assist me in this? TIA
=SWITCH(G15, G15 < G13, "Under", G15 >= G13, "Fine", G15 > G13*1.3, "Over")
In your second SWITCH formula, the second condition is true for both the second and third condition and so the third condition is never reached. Flip the second and third condition placements.
=if(count(F13, F15)=2, IFS(F15<F13, "under", F15>F13*1.3, "over", F15>=F13, "enough"), "")

Counting unique login using Map Reduce

Let say I have a very big log file with this kind of format( based on where a user login )
UserId1 , New York
UserId1 , New Jersey
UserId2 , Oklahoma
UserId3 , Washington DC
....
userId999999999, London
Note that UserId1 logged in New York first and then he flied to New Jersey and logged again from there.
If I need to get how many unique user login (means 2 login will same userid considered as 1 login), how should I map and reduce it?
My initial plan is that I want to map it first to this kind of format :
UserId1, 1
UserId1, 1
UserId2, 1
UserId3, 1
And then reduce it to
UserId1, 2
UserId2, 1
UserId3, 1
But would this cause the output to be still big in number (Especially if common behaviour of user is to login 1 or 2 times a day ). Or is there a better way to implement this?
Do map-reduce.
For example, you have 10000 lines of data, but you can only process 1000 lines of data in a time.
Then, process 1000 lines of data for 10 times.
If the sum of lines of the 10 processing's result > 1000:
do the above step again.
else:
use set directly.
I recommend making use of a custom key in the map phase. You can refer the tutorial here for writing and using custom keys. The custom key should have two parts 1) userid 2)placeid. So essentially in the mapper phase you are doing this.
emit(<userid, place>, 1)
In the reduce phase, you just have to access the key and emit the two parts of the key separately.

Extracting dollar amounts from existing sql data?

I have a field with that contains a mix of descriptions and dollar amounts. With TSQL, I would like to extract those dollar amounts, then insert them into a new field for the record.
-- UPDATE --
Some data samples could be:
Used knife set for sale $200.00 or best offer.
$4,500 Persian rug for sale.
Today only, $100 rebate.
Five items for sale: $20 Motorola phone car charger, $150 PS2, $50.00 3 foot high shelf.
In the set above I was thinking of just grabbing the first occurrence of the dollar figure... that is the simplest.
I'm not trying to remove the amounts from the original text, just get their value, and add them to a new field.
The amounts could/could not contain decimals, and commas.
I'm sure PATINDEX won't cut it and I don't need an extremely RegEx function to accomplish this.
However, looking at The OLE Regex Find (Execute) function here, appears to be the most robust, however when trying to use the function I get the following error message in SSMS:
SQL Server blocked access to procedure 'sys.sp_OACreate' of component
'Ole Automation Procedures' because this component is turned off as
part of the security configuration for this server. A system
administrator can enable the use of 'Ole Automation Procedures' by
using sp_configure. For more information about enabling 'Ole
Automation Procedures', see "Surface Area Configuration" in SQL Server
Books Online.
I don't want to go and changing my server settings just for this function. I have another regex function that works just fine without changes.
I can't imagine this being that complicated to just extract dollar amounts. Any simpler ways?
Thanks.
CREATE FUNCTION dbo.fnGetAmounts(#str nvarchar(max))
RETURNS TABLE
AS
RETURN
(
-- generate all possible starting positions ( 1 to len(#str))
WITH StartingPositions AS
(
SELECT 1 AS Position
UNION ALL
SELECT Position+1
FROM StartingPositions
WHERE Position <= LEN(#str)
)
-- generate possible lengths
, Lengths AS
(
SELECT 1 AS [Length]
UNION ALL
SELECT [Length]+1
FROM Lengths
WHERE [Length] <= 15
)
-- a Cartesian product between StartingPositions and Lengths
-- if the substring is numeric then get it
,PossibleCombinations AS
(
SELECT CASE
WHEN ISNUMERIC(substring(#str,sp.Position,l.Length)) = 1
THEN substring(#str,sp.Position,l.Length)
ELSE null END as Number
,sp.Position
,l.Length
FROM StartingPositions sp, Lengths l
WHERE sp.Position <= LEN(#str)
)
-- get only the numbers that start with Dollar Sign,
-- group by starting position and take the maximum value
-- (ie, from $, $2, $20, $200 etc)
SELECT MAX(convert(money, Number)) as Amount
FROM PossibleCombinations
WHERE Number like '$%'
GROUP BY Position
)
GO
declare #str nvarchar(max) = 'Used knife set for sale $200.00 or best offer.
$4,500 Persian rug for sale.
Today only, $100 rebate.
Five items for sale: $20 Motorola phone car charger, $150 PS2, $50.00 3 foot high shelf.'
SELECT *
FROM dbo.fnGetAmounts(#str)
OPTION(MAXRECURSION 32767) -- max recursion option is required in the select that uses this function
This link should help.
http://blogs.lessthandot.com/index.php/DataMgmt/DataDesign/extracting-numbers-with-sql-server
Assuming you are OK with extracting the numeric's, regardless of wether or not there is a $ sign. If that is a strict requirement, some mods will be needed.