Replace custom function in Google Sheets with standard functions - google-apps-script

I have a range of cells, and I want to accrue the number of times a column has the max value for its given row.
Sample:
headers -> a b c d e f g h
0 0 12 18* 1 0 0 0
30* 0 15 25 0 0 0 0
35 0 19 31 0 0 31 50*
40 10 19 31 0 2 5 55*
expected:
#max val per row-> 1 0 0 1 0 0 0 2
The maximum values are marked with an asterisk. The column a scores 1 because it has the maximum value in the second data row, the column d scores 1 as well because it has the maximum value in the first data row and the column h scores 2 because it has the maximum value in the third and fourth data rows. The rest of columns don't have the maximum value in any row, so they get a 0.
For just one row, I can copy this formula for for each column and it would do it, but I need something that applies the max row-wise COUNTIF(B2:B10, MAX($B2:$B10)).
I have written this google apps script, but I don't like its responsiveness (seeing the "Loading..." in the cell for almost a second is kind of exasperating compared with the snappiness you get with native functions):
function countMaxInRange(input) {
return [input.map(function(row) {
var m = Math.max.apply(null, row);
return row.map(function(x){return x === m && 1 || 0});
}).reduce(function(a, b){
var s = Array(a.length);
for (var i = 0; i < a.length; i++) {
s[i] = (a[i] + b[i]) || 0;
}
return s;
})];
}
Any ideas on how I could replace that code with built in functions? I don't care adding auxiliar rows or columns, as long as it is a constant number of them (that is, if I extend my dataset I don't want to manually add more helper rows or columns for each new data row or column).
I think I could add an extra column that collects the header of the column with the max value for each row; and then for each data column count how many times their header appears in that auxiliar column, but does not seem very clean.

FORMULA
=ArrayFormula(TRANSPOSE(
MMULT(
N(TRANSPOSE(NamedRange1)
=
INDEX(
QUERY(TRANSPOSE(NamedRange1),
"SELECT "&JOIN(",",("MAX(Col"&TRANSPOSE(ROW(NamedRange1))-INDEX(ROW(NamedRange1),1)+1)&")"
)),
2)
),
SIGN(ROW(NamedRange1))
)
))
where NamedRange1 is named range referred to the range.
Conditional formatting:
Apply to range: A1:H4
Custom formula: =A1=MAX($A1:$H1)
Explanation
Summary
The above formula no requires extra columns, just to set the range as a named range. In the formula NamedRange1 was used but it could be customized according to your preferences.
The result is a 1 x n array where n is the number of columns of NamedRange1. Each column will have the count of occurrences of maximum values by row on the correspondent column.
Featured "hacks"
ARRAYFORMULA returns an array of values.
Ranges greater than 1 x 1 are handled as arrays.
Using an array as argument with some functions and operators works in a similar way than a loop. In this case, this features is used to create a SQL statement to get the maximum value of each column of the input data. Note that the input data for QUERY is the transpose of NamedRange1.
N coerce TRUE/FALSE values to 1/0 respectively.
MMULT is used to make sums by rows
Note: the +0 shown on the image was inserted to force Google Sheets to keep the breaklines introduced on an edit of the formula without breaklines because if there are not significant changes to the formula, the breaklines are automatically removed due to the formula/result caching feature of Google Sheets.
Reference
MMULT Usage by Adam Lusk.

Related

SSRS Conditional Max

I would like my expression to return the max value of a column where another column equals "0".
example :
0 12
0 11
0 7
1 3
1 40
1 1
This should return 12.
I tried several things but can't make it work.
Any ideas?
Try something like.
=MAX(IIF(Fields!ColumnA.Value = 0, Fields!ColumnB.Value, -99999))
Column A and B refer to your unnamed columns in your sample data. The -99999 should be a value lower than the lowest Columb B value you will ever get. If Column B is always positive then any negative value or even 0 will suffice here.
The expression reads:
"for each row, look in Column A. If Column A is zero then return Column B's value, if Column A is not zero, return -99999. Now get the MAX value from these values"

Add Column in Table with conditional in block WHERE

I was doing a query with MySQL to save all objects returned, but I'd like identify these objects based in statements of the block WHERE, that is, if determined object to satisfy the specific characteristic I'd like create one column and in this column I assignment the value 0 or 1 in the row corresponding the object if it satisfy or not satisfy these characteristic.
This is my script:
SELECT
s.id, al.ID, al.j, al.k, al.r, gal.i
FROM
datas as al
WHERE
AND s.id = al.ID
AND al.j between 1 and 1
AND al.k BETWEEN 15 and 16
AND al.r BETWEEN 67 and 72
The script above is working perfectly and I can to save all objects which it return.
So, I'd like to know if is there a way add in the query above, on block WHERE, the following statement,
( Flags & (dbo.environment('cool') +
dbo.environment('ok') -
dbo.environment('source')) ) = 25
and ((al_pp x al_pp1)-0.5/3=11
and determined the objects that satisfy or not these condition with 0 or 1 in a new column created in Table saved.
I read some tutorials about this and saw some attempts with IF, CASE, ADD COLUMN or WHEN, but none of these solved.
Thanks in advance
MySQL has if function, see here
So you can simply use it in your query:
SELECT IF(( Flags & (dbo.fPhotoFlags('SATURATED') +
dbo.fPhotoFlags('BRIGHT') +
dbo.fPhotoFlags('EDGE')) ) = 0
and petroRad_r < 18
and ((colc_u - colc_g) - (psfMag_u - psfMag_g)) < -0.4
, 1 --// VALUE IF TRUE
, 0 --// VALUE IF FALSE
) as conditional_column, ... rest of your query

SQLite SELECT statement for column name where column has a value

What SQLite statement do I need to get the column name WHERE there is a value?
COLUMN NAME: ALPHA BRAVO CHARLIE DELTA ECHO
ROW VALUE: 0 1 0 1 1
All I want in my return is: Bravo, Delta, Echo.
Your request is not entirely clear, but you appear to be asking for a SELECT statement that will return not data but rather columns names, and not a predictable number of values but rather a number values that depend on the data in the table.
For instance,
A B C D E
0 1 0 1 1
would return (B,D,E) whereas
A B C D E
1 0 1 0 0
would return (A, C).
If that's what you're asking, this is not something that SQL does. SQL retrieves data from the table and an SQL result set always has the same number of columns per row.
To accomplish your goal, you would have to retrieve all columns that might have a value in the table and then, in your program code, check for the value in each column and accrue a list of column names that had values.
Also, consider what happens when there is more than one row to examine and the distribution of values differ. In other words, what's the expected result if the data looks like this:
A B C D E
- - - - -
0 1 0 1 1
1 0 1 0 0
[Also, note that all the columns in your example have values, some 0, some 1. What you really want is a list of column names where the column contains a value of 1.]
Finally, consider that your inability to easily get the results you need from your data might indicate a flaw in the data model you're using. For instance, if you were to structure your data like this:
TagName TagValue
------- --------
Alpha 0
Bravo 1
Charlie 0
Delta 1
Echo 1
you could then obtain your results with SELECT TagName FROM Tags WHERE TagValue = 1.
Furthermore, if 0 and 1 are really the only two possible values (indicating boolean "presence" or "absence" of the tag) then you could remove the TagValue column and the rows for Alpha and Charlie entirely (you'd INSERT a row into the table to add tag and DELETE a row to remove it).
A design along these lines seems to model your data more accurately and allows you to entire new tags to the system without having to issue an ALTER TABLE command.
http://sqlfiddle.com/#!9/1407e/1
SELECT CONCAT(IF(ALPHA,'ALPHA,',''),
IF(BRAVO,'BRAVO,',''),
IF(CHARLIE,'CHARLIE,',''),
IF(DELTA,'DELTA,',''),
IF(ECHO,'ECHO',''))
FROM table1

How can i get RowNumber Matrix in SSRS Report

i am creating a matrix report.
need to show row number in the Matrix table under column and row grouping,
like this
A B C
X 1 1 1
Y 2 2 2
Z 3 3 3
Presently i am using this Expression for Row number but i am getting incorrect count.
=RunningValue(CountDistinct("YourTableName"),Count,"YourTableName")
Riddle-Master has a decent answer if your matrix is 100% full, ie there are no empty cells.
RowNumber("DataSet1") will contain the running sum of all fields
RowNumber("RowGroup") will contain the number of fields in each row group
However, if you have empty cells, you'll end up with some fractions and staggered numbers.
I found what I believe to be a better answer on this site, as long as you have a value in each row that is unique from the last. In my case, I'm using Customer_Num.
Go to Report Properties, open the Code property and paste the following code:
public dim LastNum as String
public dim rowCount as int32 = 0
Public Function GetRowNum(byval Num as String) as Integer
if Num <> LastNum then
rowCount = rowCount + 1
LastNum = Num
End If
Return rowCount
End Function
Then in the cell where you want the Row Number, past the following expression:
=Code.GetRowNum(Fields!Customer_Num.Value)
This should compare each value against the previous for each row, and give you an incrementing row number, no matter how many cell values are in each row.
From my experience RowNumber alone would give the sum all the dynamic fields from every row.
But a RowNumber with a scope on one field only would give the sum of the dynamic fields on one row alone.
Thus what solved it for me was:
=RowNumber("DataSet1")/RowNumber("StudentId")
When DataSet1 is from where I take all my matrix info and StudentId is only one of the fields in a row.
What worked for me for a matrix with both row and column grouping is:
=RowNumber("YourColumnGroupName") / CountRows()

Report and Graphic in access 2007 - calculating values on queries

Picture a table with fields (Id, Valid, Value)
Valid = boolean
Value = number from 0 to 100
What I want is a report that counts the number of records where (valid = 0), and then gives me the total number of cases where (value < 70) and the number of cases where (value >= 70).
The problem is that the "value" field could be empty on some of the records and I only want the records where the value field is not empty.
I know that the second value (value>=70) is going to be calculated, but the problem is that I can't simply do (total number of records - number of records where value < 70), because there's the problem with the records where "value" is null...
And then I want to create graphic with these values, to see the percentage of records below and above 70.
"The problem is that the "value" field could be empty on some of the records and I only want the records where the value field is not empty."
Use a WHERE clause to exclude rows whose "value" field is Null.
Here is sample data for tblMetraton.
Id Valid Valu
1 -1 2
2 0 4
3 -1 6
4 0
5 0 90
I used Valu for the field name because Value is a reserved word.
You can use the Count() function in a query and take advantage of the fact it only counts non-Null values. So use Count() with an IIf() expression which returns a non-Null value (I used 1) for the condition you want to match and Null otherwise.
SELECT
Count(IIf(Valid=0,1,Null)) AS valid_false,
Count(IIf(Valu<70,1,Null)) AS below_70,
Count(IIf([Valu]>=70,1,Null)) AS at_least70
FROM tblMetraton AS m
WHERE (((m.[Valu]) Is Not Null));
Based on my sample data in tblMetraton, that query gives me this result set.
valid_false below_70 at_least70
2 3 1
If my sample data does not address the variability you're dealing with, and/or if my query results don't match your requirements, please show us you own sample data and the results you want based on that sample.