Calculate time differences and sum duration - google-sheets

I am trying to create a small "app" using tasker on my android phone that am supposed to track my workhours and over/under-time. I have managed to get tasker to send timestamps on the start/end of each workday and are writing them to a google sheet so it gets recorded like:
<Not implemented> <Not implemented>
| A | B | C | D | E | F |
| 2020-01-29 | 07:24 | 16:33 | 00:09 | | -02:51 |
| 2020-01-30 | 07:00 | 12:00 | -03:00 | | |
Where the "D" column is the difference between ordinary workhours (8) and actually registred hours.
The "F" column should summarize the "D" column and show the sum of all values.
The data in the three first columns are beeing sent correctly but I cant figure out how to set up formulas so that the values for the "D" column is added and and same thing with the cell in the "F" column. I have been trying to change to different formats and tried creating my own formats to but do not understand how to get it to work.

I'm getting a different result than you in D1. I wonder if you're also accounting for a lunch hour (so subtract 9 instead of 8), but these formulas worked for me:
in Column D: =(C1-B1)-(8/24)
in Cell F1: =sum(D1:D2)
Column D and Cell F1 are formatted as Time > Duration.
Here's the result:

Related

Can I order a pivot table using a second condition?

I am working with a spreadsheet where I store the books I read. The format is as follows:
A | B | C | D | E | F
year | book | author | mark | language | country of the author
With entries like:
A | B | C | D | E | F
-------------------------------------------------------------
2004 | Hamlet | Shakespeare | 8 | ES | UK
2005 | Crimen y punishment | Dostoevsky | 9 | CAT | Russia
2007 | El mundo es ansí | Baroja | 8 | ES | Spain
2011 | Dersu Uzala | Arsenyev | 8 | EN | Russia
2015 | Brothers Karamazov | Dostoevsky | 8 | ES | Russia
2019 | ... Shanti Andía | Baroja | 7 | ES | Spain
I have several pivot tablas to get different data, such as top countries, top books, etc. In one of them I want to group by authors and order by number of books I have read from each one of them.
So I defined:
ROWS
author (column C) with
order: Desc for COUNT of author
VALUES
author
summation by: COUNT
show as Default
mark
summation by: AVERAGE
show as Default
This way, the data above show like this:
author | COUNT of author | AVERAGE of mark
-------------------------------------------------------------
Baroja | 2 | 7,5
Dostoevsky | 2 | 8,5
Shakespeare | 1 | 8
Arsenyev | 1 | 8
It is fine, since it orders data having top read authors on top. However, I would also like to order also by AVERAGE of mark. This way, when COUNT of author matches, it would use AVERAGE of mark to solve the ties and put on top the one author with a better average on their books.
On my sample data, Dostoevsky would go above Baroja (8,5 > 7).
I have been looking for different options, but I could not find any without including an extra column in the pivot table.
How can I use a second option to solve the ties when the first option gives the same value?
You can achieve a customized sort order on a pivot table without any extra columns in the source range. However... you'd definately need an extra field added to the pivot.
In the Pivot table editor go to Values and add a Calculated Field.
Use any formula that describes the sort order you want. E.g. let's multiply the counter by 100 to use as first criteria:
=COUNTA(author) * 100 + AVERAGE(score)
Do notice it is important to select Summarize by your Custom formula (screenshot above).
Now, just add this new calculated field as your row's Sort by field, and you're done!
Notice though, you do get an extra column added to the pivot.
Of course, you could hide it.
Translated from my answer to the cross-posted question on es.SO.
try:
=QUERY(A2:F,
"select C,count(C),avg(D)
where A is not null
group by C
order by count(C) desc
label C'author',count(C)'COUNT of author',avg(D)'AVERAGE of mark'")

Google Sheets Formula to calculate actual total duration of tasks with different start/end dates, overlaps, and gaps

I know I how to do this using a custom function/script but I am wondering if it can be done with a built-in formula.
I have a list of tasks with a start date and end date. I want to calculate the actual # of working days (NETWORKDAYS) spent on all the tasks.
Task days may overlap so I can't just total the # of days spent on each task
There may be gaps between tasks so I can't just find the difference between the first start and last end.
For example, let's use these:
| Task Name | Start Date | End Date | NETWORKDAYS |
|:---------:|------------|------------|:-----------:|
| A | 2019-09-02 | 2019-09-04 | 3 |
| B | 2019-09-03 | 2019-09-09 | 5 |
| C | 2019-09-12 | 2019-09-13 | 2 |
| D | 2019-09-16 | 2019-09-17 | 2 |
| E | 2019-09-19 | 2019-09-23 | 3 |
Here it is visually:
Now:
If you total the NETWORKDAYS you'll get 15
If you calculate NETWORKDAYS between 2019-09-02 and 2019-09-23 you get 16
But the actual duration is 13:
A and B overlap a bit
There is a gap between B and C
There is a gap between D and E
If I was to write a custom function I would basically take all the dates, sort them, find overlaps and remove them, and account for gaps.
But I am wondering if there is a way to calculate the actual duration using built-in formulas?
sure, why not:
=ARRAYFORMULA(COUNTA(IFERROR(QUERY(UNIQUE(TRANSPOSE(SPLIT(CONCATENATE("×"&
SPLIT(REPT(INDIRECT("B1:B"&COUNTA(B1:B))&"×",
NETWORKDAYS(INDIRECT("B1:B"&COUNTA(B1:B)), INDIRECT("C1:C"&COUNTA(B1:B)))), "×")+
TRANSPOSE(ROW(INDIRECT("A1:A"&MAX(NETWORKDAYS(B1:B, C1:C))))-1)), "×"))),
"where Col1>4000", 0))))

How to use ARRAYFORMULA to work with an array of array

I'm currently working on a formula but I can't seem to make it work the way I intend to.
The column A of the spreadsheet look like something like that:
| A |
| B |
| C |
| D |
| E |
And what I am trying to do is get an output like that:
| A |
| A | B |
| A | B | C |
| A | B | C | D |
| A | B | C | D | E |
So I tried using offset, to get from the first line to the current line for each of my lines.
=ARRAYFORMULA(TRANSPOSE(OFFSET(A1;0;0;ROW(A1:A5)))
But since ROW(A1:A5) doesn't return an array the cell was just | A |
So I tried adding ARRAYFORMULA around the ROW(A1:A5) and what I go was:
| 1 |
| 2 |
| 3 |
| 4 |
| 5 |
Which is what I need! But if I add it to the original function, I still only get | A |
Is there a way for me to "force" ARRAYFORMULA to run on A1:A5 so that I get the required output?
Additionnal data
I know this would be easier to do with a script but a script solution is not what I'm looking for. I'm trying to understand why it does that and how to prevent it.
This formula is meant to be used inside another so I need it to be only 1 formula, I can't use the cross to expand it.
I don't mind if the solution isn't showable (if the array superpose itself by example).
I made a demo here.
I also tried with INDIRECT instead of OFFSET to get the ranges and I had the same results.
Please try, somewhere in the Row1, assuming that is where your first A is, and copied down to suit:
=SPLIT(JOIN("|",A$1:A1),"|")
(as an array formula, if you must.)
=ARRAYFORMULA(IF(ROW(A2:A6)>=TRANSPOSE(ROW(A2:A6));TRANSPOSE(A2:A6);))
ROW() is used to create series of vertical numbers,which are compared against the same series of numbers horizontally to create a 5x5 matrix of TRUE/FALSE,which can then easily be extrapolated to the desired output.
Assuming your data is located at A1:A8 enter this formula at C1 then copy it to C2:C8:
= TRANSPOSE ( ARRAY_CONSTRAIN( $A$1:$A$8 ,
1 + ROW() - ROW( $C$1 ) , 1 + COLUMN() - COLUMN( $C$1 ) ))

Get a row from a range based on a single value in column

I'm using a spreadsheet to store highscores. I have one column (Initials [Column D]) and one column (Scores [Column E]). They are already sorted from highest to lowest (dependent upon the Scores). I want to get the first occurrence of all initials and that initials score.
For example if I had this:
|Initials|Scores|
| ABC | 5 |
| NOT | 4 |
| ABC | 2 |
| LOL | 1 |
I want to get this:
|Initials|Scores|
| ABC | 5 |
| NOT | 4 |
| LOL | 1 |
I've been able to get just the names portion with =UNIQUE(D:D), but how would one also get the scores from the next column? I've been trying for a while now, and can't figure it out.
Since the values in E are already sorted, try:
=ArrayFormula(vlookup(unique(filter(D2:D, len(D2:D))), D2:E, {1,2}, 0))
of if you want to use a limited range:
=ArrayFormula(vlookup(unique(D2:D50), D2:E50, {1,2}, 0))
See if that works ?

Trying to find a Google Spreadsheet formula or query for this example

A | B | C | D | E | F | G
name|num|quant|item|quant2
car | 5 | 100 |
| | |wheel| 4
| | |axel | 2
| | |engine|1
truck| 2 | 20 |
| | |wheel| 6
| | |bed | 1
| | | axel| 2
I need a formula which will do B*C*E. the tables look like this, so it needs to be something like
=b$2*c$2*e3 and then dragged.... and then the next set, b$6*c$6*e7 and dragged, etc but i want sure how to get the cieling sort of something. if b5 is empty, look at each above until it finds the one not filled.
I am trying to use this to get total quantity of parts per car, truck etc.... and then group by part.
I dont have a set of DB tables to do this, just a spreadsheet.
I had to add some additional information to resolve this.
I was thinking there would be a way to do a google script that would do this and update the file, but i couldnt seem to find it.
I first summed each group item:
=b$3*e4
and dragged for that grouping.
Then afterwards, i went to a selection of space and wrote up a query.
=query(D:F, "select D,sum(F) group by D")

Resources