excel within range of cells, is there a date entered - arrays

Having some columns with either empty or a date in it, I need to get a true or false for a date present.
A B C D E F
1 Name oDate eDate xDate EndDate Status
2 Lars 01-11-2015 ? <= TRUE
3 Erik ? <= FALSE
4 Niels 09-01-2015 10-02-2015 ? <= TRUE
5 Jens 02-02-2016 10-02-2015 ? <= TRUE
Tried with
=IF(COUNTIFS($AP2:$AP2;ISNUMBER($AP2);$AQ2:$AQ2;ISNUMBER($AQ2);$AR2:$AR2;ISNUMBER($AR2);$AS2:$AS2;ISNUMBER($AS2);$AT2:$AT2;ISNUMBER($AT2);$AU2:$AU2;ISNUMBER($AU2)) >= 1;"TRUE";"FALSE")
but that just checks if fields not empty.
Anyone?

To Excel dates are just numbers formatted to suit (subject to being in the range 0 - 2958465) so say 23 September 1904 is just the same as dozen gross (1,728) without added context such as formatting. Provided the formatting is as you show it can be detected to use to differentiate say 11/02/2015 from 42,046:
=OR(CELL("format",B2)="D1",CELL("format",C2)="D1",CELL("format",D2)="D1",CELL("format",B2)="D1")
However since detecting the format of cells rather than content, a blank cell formatted as a date will count even without, in that case 00/01/1990 being displayed. (So you might also want a further check, such as that the sum of B:E cells is also greater than 0, or that each is a positive number and not text.)

Related

Set Analysis date, 2 conditions, max date - 1

I have a set analysis and need to restrict the range of the maxmim date to -1 -
=max({<BREAK={'5Days'}>}date(DATE))
I tried like this but I have an error -
=max({<BREAK={'5Days'}, DATE = {Today()-1}>}date(DATE)) and
=max({<BREAK={'5Days'}>+< DATE = {Today()-1}>}date(DATE))
Do you have any other idea?
I solved it like this -
=max({<BREAK={'5Days'}>}date((DATE)-1))
and it worked perfectly. In fact it gave the maximum date - 1.

Google Sheets: ArrayFormula sumifs, but return some symbol or empty cell if there's nothing to sum

I have the following table:
`Jan` `Feb` `Mar`
`P7` `Q7` `R7` 56.80 0 0
`Column E Column I Column N`
17 expense Jan-5 15.87
18 $ Jan-9 56.80
19 expense Feb-8 38.12
20 expense Mar 5 45.38
21 $ Mar-12 0.00
So I have `Cell P7` with the following formula `=ArrayFormula(sumifs(N17:N,E17:E,"$",MONTH(I17:I),1))`
and `Cell Q7` with the following formula
`=ArrayFormula(sumifs(N17:N,E17:E,"$",MONTH(I17:I),2))`
and `Cell R7` with the following formula
`=ArrayFormula(sumifs(N17:N,E17:E,"$",MONTH(I17:I),3))`
that checks `Column I` for January dates (for `P7`), February dates (for `Q7`) and March dates (for `R7`), then checks if there's at least one sign `$` in corresponding `Column E` for those dates, and if there is, sums all corresponding amounts in `Column N`.
Now, my problem is this: the formula, as it is now, returns `0` even if there are no signs `$` for a specific month range, like for February in the above table. There are no `$` sign in `Column E` for February, yet cell `Q7` shows `0`.
I would like it to:
- return nothing at all (empty cell instead of `0`) if there are no amounts in `Column N` for a specific month marked with `$` sign in `Column E`
- return `0` only if there is `0.00` amount in `Column N` along with the `$` sign in corresponding `Column E`.
or
- return something else, like `~`, if there's nothing to sum up.
Let's say for March I could put `$` in `E21` and `~` in `N21` and see that `~` returned in `R7` if there are no more amounts to sum up.
Is there a way to do it?
Thanks to MAttKing's reference, simply add your formula in IFERROR(1/(1/ ComplexFunction() )) which should look something like this.
=IFERROR(1/(1/ArrayFormula(sumifs(D3:D,A3:A,"$",MONTH(B3:B),2))))
Output:

How to get row limiting by value from two columns

Please advice how to combine query, to find first occurrence of row
I have table
Date Counter
01.01.2005 208,5
02.01.2005 209,5 <----- start
03.01.2005 210,5
04.01.2005 211,5
08.01.2005 16,5
09.01.2005 17,2
10.01.2005 18,8 <------ correct
11.01.2005 19,7
12.01.2005 20,7
13.01.2005 21
14.01.2005 116,3
15.01.2005 120,4
16.01.2005 135,2
17.01.2005 1,1
18.01.2005 10,3
19.01.2005 18,7 <------ wrong
20.01.2005 14,2
21.01.2005 8,5
22.01.2005 7,1
and I need to extract Date by Counter 18.5 (from starting date 02.01.2005), since this value not in the table possible to take next higher value.
I tried to search by using starting date (because table have thousand dates and Counter between 0-499) and limit for value (grater or equal).
select top 1 Date from Tabel1 where Date > 02.01.2005 AND Counter >= 18.5
this query return wrong result - date 03.01.2005,
but correct must be 10.01.2005.
Hope for any assistance. Thanks in advance.
(I use: sql 2008 r).
You need to put an ORDER BY clause when using TOP. In this case you want to get the lowest Counter:
SELECT TOP 1 *
FROM tbl
WHERE
Date > CAST('20050102' AS DATE)
AND Counter >= 18.5
ORDER BY Counter
Note that without the ORDER BY, the result of TOP 1 is not guaranteed to always be the same.

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?

Converting text to Datetime in specific format

I need an expression which will convert a text (VARCHAR) column to a DATETIME if, and only if, it matches dd/MM/yyyy, d/MM/yyyy, dd/M/yyyy or d/M/yyyy. If it doesn't match then I want a NULL.
I have this...
CASE ISDATE([DateField])
WHEN 1 THEN CONVERT(DATETIME,[DateField],103)
ELSE NULL
END
However this fails for '15/04/76' for example - with a "Conversion failed when converting datetime from character string" error - whereas I would want it to return NULL
Example output
'1/6/1976' -> 1976-06-01
'01/06/1976' -> 1976-06-01
'13/06/2001' -> 2001-06-13
'06/13/2001' -> NULL
'13/06/76' -> NULL
Is there a way of forcing ISDATE to validate a given format?
The documentation seems to suggest so...
ISDATE is deterministic only if used with the CONVERT function, the
CONVERT style parameter is specified and style is not equal to 0, 100,
9, or 109.
But ISDATE only takes one argument, so how do I "use it with CONVERT function" if I am not doing so already?
You could do a nested case statement here. The first could check to see if you have a 10 character string 2 for day, 2 for month, 4 for year and 2 for separators = 10 characters.
SET DATEFORMAT DMY;
Case When DateField Like '%/%/[0-9][0-9][0-9][0-9]'
Then Case When IsDate(DateField) = 1
Then CONVERT(DATETIME,[DateField],103)
End
End
Revised: I changed the code to use a like search which forces there to be a /YYYY at the end of the string, and then does an IsDate check to allow for a single day and/or month.
Well, first off, why on earth are you storing datetime values in a varchar column? This is a cardinal sin for a variety of reasons, not the least of which is that you get no validation whatsoever that the data is (or is convertible to) a datetime. You should also consider validating the input, even if you leave the column as varchar, so you don't have such a wide variety of potential formats that you want to consider valid.
So here is one way, borrowing a bit from #G Mastros:
DECLARE #f TABLE(i INT, d VARCHAR(32));
INSERT #f VALUES
(1,'15/04/76'),
(2,'15/04/1976'),
(3,'1/3/1976'),
(4,'1/3/76'),
(5,'15/3/1976'),
(6,'22/22/22'),
(7,'Yesterday');
SET DATEFORMAT DMY;
SELECT i, d, d2 = CASE WHEN ISDATE(d) = 1
AND d LIKE '%/[0-9][0-9][0-9][0-9]'
THEN CONVERT(DATETIME, d, 103) END
FROM #f;
Results:
i d d2
- ---------- -----------------------
1 15/04/76 NULL
2 15/04/1976 1976-04-15 00:00:00.000
3 1/3/1976 1976-03-01 00:00:00.000
4 1/3/76 NULL
5 15/3/1976 1976-03-15 00:00:00.000
6 22/22/22 NULL
7 Yesterday NULL
PS this will be a great case for TRY_CONVERT in SQL Server 2012. It does exactly what you're asking - it tries to convert to the specified data type; if it can't, it returns NULL.
Thanks for the responses folks.
I've done it like this...
CASE ISDATE([DateField]) WHEN 1 THEN
CASE WHEN SUBSTRING([DateField],LEN([DateField])-4,1) = '/' THEN
CASE WHEN CHARINDEX('/',[DateField],LEN([DateField])-3)=0 THEN
CONVERT(datetime, [DateField] , 103)
END
END
END
which is pretty nasty business so would still appreciate something neater!
But this doesn't work either - it still errors on mm/dd/yyyy format dates!
Scrap that last comment - it does seem to work now? Probably something to do with SET DATEFORMAT

Resources