<?xml version="1.0" encoding="UTF-8"?>
<rss xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#" xmlns:taxo="http://purl.org/rss/1.0/modules/taxonomy/" version="2.0">
  <channel>
    <title>topic Re: Find overlapping on dates in SAS Programming</title>
    <link>https://communities.sas.com/t5/SAS-Programming/Find-overlapping-on-dates/m-p/398224#M96295</link>
    <description>Interesting solution, I wouldn't come up with that.&lt;BR /&gt;My take would probably be first sort by client is and date begin.&lt;BR /&gt;Then a data step with RETAIN on a variable you set ronthe previous date end, and check if it's in the date begin and end interval. No idea If that's more efficient than yours - a log could give a clue.</description>
    <pubDate>Fri, 22 Sep 2017 21:17:52 GMT</pubDate>
    <dc:creator>LinusH</dc:creator>
    <dc:date>2017-09-22T21:17:52Z</dc:date>
    <item>
      <title>Find overlapping on dates</title>
      <link>https://communities.sas.com/t5/SAS-Programming/Find-overlapping-on-dates/m-p/398219#M96290</link>
      <description>&lt;P&gt;Hello,&lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;I have a problem where I have to find contracts from clients that have overlapping durations as it is supposed that a client cannot have two or more active contracts.&lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;I have created the following code, but I think this is not the best way to go, since it takes a lot of time on big tables.&lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;does anyone have an idea on how I can Improve the performance on this?&lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;PRE&gt;&lt;CODE class=" language-sas"&gt;data test;
	infile datalines;
	input client_Id $ contract $ date_begin date_end;
	informat date_begin date_end ddmmyy10.;
	format date_begin date_end date7.;
	cards;
10 A 01/09/2016 30/09/2016
10 B 10/12/2016 24/12/2016
10 C 28/09/2016 07/10/2016
11 D 01/12/2016 24/12/2018
12 E 15/01/2016 07/03/2016
12 F 08/12/2016 24/12/2016
12 G 06/03/2016 07/11/2016
;
run;

%macro overlap;
	%let dt_ini=&amp;amp;dt_ini;
	%let dt_end=&amp;amp;dt_end;
	%let client = &amp;amp;client;
	%let sqlresults =;

	proc sql noprint;
		select count(*) into :sqlresults 
		from TEST 
		where client_id=&amp;amp;client and  
		(date_begin between &amp;amp;dt_ini and &amp;amp;dt_end
		or date_end between &amp;amp;dt_ini and &amp;amp;dt_end);
	QUIT;

	%let sqlresults = &amp;amp;sqlresults;
%mend;

proc fcmp outlib=work.testing.funcs;
	function get_overlap(dt_ini, dt_end, client $);
	rc=run_macro('overlap', dt_ini, dt_end, client, sqlresults);
	return (sqlresults);
	endsub;
	quit;
	
options cmplib=work.testing;

data test2;
	set test;
	date_overlap=get_overlap(date_begin, date_end, client_id)-1;
run;&lt;/CODE&gt;&lt;/PRE&gt;
&lt;P&gt;Edit via&amp;nbsp;&lt;a href="https://communities.sas.com/t5/user/viewprofilepage/user-id/13879"&gt;@Reeza&lt;/a&gt;&amp;nbsp;to format code for legibility.&lt;/P&gt;</description>
      <pubDate>Fri, 22 Sep 2017 20:17:58 GMT</pubDate>
      <guid>https://communities.sas.com/t5/SAS-Programming/Find-overlapping-on-dates/m-p/398219#M96290</guid>
      <dc:creator>iscgonzalez</dc:creator>
      <dc:date>2017-09-22T20:17:58Z</dc:date>
    </item>
    <item>
      <title>Re: Find overlapping on dates</title>
      <link>https://communities.sas.com/t5/SAS-Programming/Find-overlapping-on-dates/m-p/398224#M96295</link>
      <description>Interesting solution, I wouldn't come up with that.&lt;BR /&gt;My take would probably be first sort by client is and date begin.&lt;BR /&gt;Then a data step with RETAIN on a variable you set ronthe previous date end, and check if it's in the date begin and end interval. No idea If that's more efficient than yours - a log could give a clue.</description>
      <pubDate>Fri, 22 Sep 2017 21:17:52 GMT</pubDate>
      <guid>https://communities.sas.com/t5/SAS-Programming/Find-overlapping-on-dates/m-p/398224#M96295</guid>
      <dc:creator>LinusH</dc:creator>
      <dc:date>2017-09-22T21:17:52Z</dc:date>
    </item>
    <item>
      <title>Re: Find overlapping on dates</title>
      <link>https://communities.sas.com/t5/SAS-Programming/Find-overlapping-on-dates/m-p/398227#M96297</link>
      <description>&lt;P&gt;Looks like your middle SQL is doing the heavy lifting here. &amp;nbsp;Why not expand that to do the whole thing?&lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;proc sql&amp;nbsp;noprint;&lt;/P&gt;
&lt;P&gt;create table want as select a.*, b.contract as overlapping_contract&lt;/P&gt;
&lt;P&gt;from have a, have b&lt;/P&gt;
&lt;P&gt;where ( (a.date_begin &amp;lt;= b.date_begin &amp;lt;= a.date_end) or (a.date_begin &amp;lt;= b.date_end &amp;lt;= a.date_end) )&lt;/P&gt;
&lt;P&gt;and a.client=b.client and a.contract ne b.contract;&lt;/P&gt;
&lt;P&gt;quit;&lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;This the idea, although you may need to fiddle with it.&lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;It's possible you could switch (or may have to switch) to BETWEEN instead of the two sets of &amp;lt;=.&lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;Also, you may want to change &amp;lt;= to get rid of the equal sign ... depends on what you consider "overlapping" to mean.&lt;/P&gt;
&lt;P&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;You can also select the overlapping dates (as long as you rename them, similarly to what was done for OVERLAPPING_CONTRACT).&lt;/P&gt;</description>
      <pubDate>Fri, 22 Sep 2017 21:32:43 GMT</pubDate>
      <guid>https://communities.sas.com/t5/SAS-Programming/Find-overlapping-on-dates/m-p/398227#M96297</guid>
      <dc:creator>Astounding</dc:creator>
      <dc:date>2017-09-22T21:32:43Z</dc:date>
    </item>
    <item>
      <title>Re: Find overlapping on dates</title>
      <link>https://communities.sas.com/t5/SAS-Programming/Find-overlapping-on-dates/m-p/398244#M96307</link>
      <description>&lt;P&gt;&lt;a href="https://communities.sas.com/t5/user/viewprofilepage/user-id/58894"&gt;@iscgonzalez&lt;/a&gt;&lt;/P&gt;
&lt;P&gt;Something like below could work and eventually performs better than a SQL as it requires only one sort step for your source data.&lt;/P&gt;
&lt;PRE&gt;&lt;CODE class=" language-sas"&gt;data test;
	infile datalines;
	input client_Id $ contract $ date_begin date_end;
	informat date_begin date_end ddmmyy10.;
	format date_begin date_end date7.;
	cards;
10 A 01/09/2016 30/09/2016
10 B 10/12/2016 24/12/2016
10 C 28/09/2016 07/10/2016
11 D 01/12/2016 24/12/2018
12 E 15/01/2016 07/03/2016
12 F 08/12/2016 24/12/2016
12 G 06/03/2016 07/11/2016
;
run;

proc sort data=test;
  by client_id date_begin;
run;

data want;
  set test;
  by client_Id;

  set test(firstobs=2 keep=client_Id contract date_begin date_end rename=(contract=contract2 date_begin=date_begin2 date_end=date_end2));

  if last.client_Id then 
    do;
      call missing(max_date_end);
      return;
    end;

  retain max_date_end;
  format max_date_end date7.;
  max_date_end=max(max_date_end,date_end);
  
  if date_begin2&amp;lt;=max_date_end then output;
run;
&lt;/CODE&gt;&lt;/PRE&gt;</description>
      <pubDate>Fri, 22 Sep 2017 23:42:53 GMT</pubDate>
      <guid>https://communities.sas.com/t5/SAS-Programming/Find-overlapping-on-dates/m-p/398244#M96307</guid>
      <dc:creator>Patrick</dc:creator>
      <dc:date>2017-09-22T23:42:53Z</dc:date>
    </item>
  </channel>
</rss>

