<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN">
<HTML><HEAD>
<META http-equiv=Content-Type content="text/html; charset=us-ascii">
<META content="MSHTML 6.00.6001.18203" name=GENERATOR></HEAD>
<BODY>
<DIV dir=ltr align=left><SPAN class=036020319-05032009><FONT face="Lucida Sans" 
color=#000080 size=2>As usual, my reaction to this code is 
'yuck'.</FONT></SPAN></DIV>
<DIV dir=ltr align=left><SPAN class=036020319-05032009><FONT face="Lucida Sans" 
color=#000080 size=2></FONT></SPAN>&nbsp;</DIV>
<DIV dir=ltr align=left><SPAN class=036020319-05032009><FONT face="Lucida Sans" 
color=#000080 size=2>I think your change is sound, and you should go 
ahead.</FONT></SPAN></DIV>
<DIV dir=ltr align=left><SPAN class=036020319-05032009><FONT face="Lucida Sans" 
color=#000080 size=2></FONT></SPAN>&nbsp;</DIV>
<DIV dir=ltr align=left><SPAN class=036020319-05032009><FONT face="Lucida Sans" 
color=#000080 size=2>A few other improvements to consider:</FONT></SPAN></DIV>
<DIV dir=ltr align=left><SPAN class=036020319-05032009><FONT face="Lucida Sans" 
color=#000080 size=2></FONT></SPAN>&nbsp;</DIV>
<DIV dir=ltr align=left><SPAN class=036020319-05032009><FONT face="Lucida Sans" 
color=#000080 size=2>1. To distinguish between a tuple-set and a member-set, see 
if you can use the type derived by the validator rather than the runtime 
'instanceof' check.</FONT></SPAN></DIV>
<DIV dir=ltr align=left><SPAN class=036020319-05032009><FONT face="Lucida Sans" 
color=#000080 size=2></FONT></SPAN>&nbsp;</DIV>
<DIV dir=ltr align=left><SPAN class=036020319-05032009><FONT face="Lucida Sans" 
color=#000080 size=2>2. The code seems to be detecting empty lists by doing a 
get(0) then handling the IndexOutOfBoundsException. I believe that the person 
who wrote the high-cardinalty dimension code did this because size() can be an 
expensive operation; but they may think that try-catch is more elegant than if, 
I don't know. It's not possible to make size() a cheap operation, but we can 
make isEmpty() efficient. Can you see whether it's possible to replace it with 
an isEmpty check?</FONT></SPAN></DIV>
<DIV dir=ltr align=left><SPAN class=036020319-05032009><FONT face="Lucida Sans" 
color=#000080 size=2></FONT></SPAN>&nbsp;</DIV>
<DIV dir=ltr align=left><SPAN class=036020319-05032009><FONT face="Lucida Sans" 
color=#000080 size=2>3. Even though I don't like the high-cardinality dimension 
code as a whole, ConcatenableList is basically sound, and worth saving. The 
change you proposed earlier, to consolidate a the sublists of ConcatenableList 
into a single array on the first call to size or get, damages the performance 
characteristics of that class. For instance, it is not worth consolidating a 
list that has two sublists of size 500K, but it is worth consolidating a list 
that has 100K lists of size 10. In particular, your approach would give O(n^2) 
performance&nbsp;if someone adds one element at a time onto the end of a 
list.</FONT></SPAN></DIV>
<DIV dir=ltr align=left><SPAN class=036020319-05032009><FONT face="Lucida Sans" 
color=#000080 size=2></FONT></SPAN>&nbsp;</DIV>
<DIV dir=ltr align=left><SPAN class=036020319-05032009><FONT face="Lucida Sans" 
color=#000080 size=2>This looks like a better algorithm: consolidate only if the 
number of sublists is greater than the square root of the number of 
elements.</FONT></SPAN></DIV>
<DIV dir=ltr align=left><SPAN class=036020319-05032009><FONT face="Lucida Sans" 
color=#000080 size=2></FONT></SPAN>&nbsp;</DIV>
<DIV dir=ltr align=left><SPAN class=036020319-05032009><FONT face="Lucida Sans" 
color=#000080 size=2>Julian</FONT></SPAN></DIV><BR>
<BLOCKQUOTE 
style="PADDING-LEFT: 5px; MARGIN-LEFT: 5px; BORDER-LEFT: #000080 2px solid; MARGIN-RIGHT: 0px">
  <DIV class=OutlookMessageHeader lang=en-us dir=ltr align=left>
  <HR tabIndex=-1>
  <FONT face=Tahoma size=2><B>From:</B> mondrian-bounces@pentaho.org 
  [mailto:mondrian-bounces@pentaho.org] <B>On Behalf Of </B>Matt 
  Campbell<BR><B>Sent:</B> Thursday, March 05, 2009 10:30 AM<BR><B>To:</B> 
  Mondrian developer mailing list<BR><B>Subject:</B> Re: [Mondrian] Re: 
  Performance degradation<BR></FONT><BR></DIV>
  <DIV></DIV>
  <DIV><BR></DIV>
  <DIV>After spending some more time looking at this issue I think the best 
  solution (at least short term), is to fix the method SetFunDef.evaluateList 
  (pasted below). &nbsp;I believe what it's intended to do is load an ArrayList 
  if the dimension in the set is not flagged as highCardinality. &nbsp;It fails 
  in certain cases, though, since the result object may be a list of lists when 
  there are multi-element tuples.</DIV>
  <DIV><BR></DIV>
  <DIV>I think a reasonable modification would be to assume the set is NOT 
  highCardinality, unless there is only a single dimension in result. This would 
  cause SetFunDef to use an ArrayList in such cases, which was the behavior 
  prior to the high cardinality changes.</DIV>
  <DIV><BR></DIV>
  <DIV>Any objections to such a change? &nbsp;</DIV>
  <DIV><BR></DIV>
  <DIV>(note that the method below is as it is currently checked in)</DIV>
  <DIV><BR></DIV>
  <DIV>
  <DIV>public List evaluateList(final Evaluator evaluator) {</DIV>
  <DIV>&nbsp;&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;this.result = new 
  ConcatenableList();</DIV>
  <DIV>&nbsp;&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;for (VoidCalc voidCalc : 
  voidCalcs) {</DIV>
  <DIV>&nbsp;&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; 
  &nbsp;voidCalc.evaluateVoid(evaluator);</DIV>
  <DIV>&nbsp;&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;}</DIV>
  <DIV>&nbsp;&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;// REVIEW: What the heck 
  is this code doing? Why is it OK to</DIV>
  <DIV>&nbsp;&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;// ignore 
  IndexOutOfBoundsException and NullPointerException?</DIV>
  <DIV>&nbsp;&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;try {</DIV>
  <DIV>&nbsp;&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;if 
  (result.get(0) instanceof Member) {</DIV>
  <DIV>&nbsp;&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; 
  &nbsp;if (!((Member)result.get(0)).getDimension()</DIV>
  <DIV>&nbsp;&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; 
  &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;.isHighCardinality()) {</DIV>
  <DIV>&nbsp;&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; 
  &nbsp; &nbsp; &nbsp;result.toArray();</DIV>
  <DIV>&nbsp;&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; 
  &nbsp;}</DIV>
  <DIV>&nbsp;&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;}</DIV>
  <DIV>&nbsp;&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;} catch 
  (IndexOutOfBoundsException iooe) {</DIV>
  <DIV>&nbsp;&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;} catch 
  (NullPointerException npe) {</DIV>
  <DIV>&nbsp;&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;}</DIV>
  <DIV>&nbsp;&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;return result;</DIV>
  <DIV>&nbsp;&nbsp; &nbsp; &nbsp; &nbsp;}</DIV></DIV><BR><BR>
  <DIV class=gmail_quote>On Wed, Mar 4, 2009 at 4:16 PM, Matt Campbell <SPAN 
  dir=ltr>&lt;<A 
  href="mailto:mkambol@gmail.com">mkambol@gmail.com</A>&gt;</SPAN> wrote:<BR>
  <BLOCKQUOTE class=gmail_quote 
  style="PADDING-LEFT: 1ex; MARGIN: 0px 0px 0px 0.8ex; BORDER-LEFT: #ccc 1px solid">Virtually 
    all the time spent on the query is spent in ConcatenableList, in the size() 
    and get() methods. &nbsp;Both have some pretty inefficient looking logic. 
    &nbsp;In get(), if the element retrieved is not the next, previous, or 
    pre-previous, then the code iterates through the whole list up to the 
    elements index. &nbsp;Similarly with .size(), the code iterates through the 
    lists, adding up each lists size. &nbsp;I'm guessing that in many cases the 
    expense of doing this once is probably about the cost of converting to an 
    ArrayList. &nbsp;As an experiment I modified .size() to always convert to an 
    ArrayList, and this cut the time to execute dramatically.
    <DIV>
    <DIV></DIV>
    <DIV class=h5>
    <DIV><BR></DIV>
    <DIV>
    <DIV>
    <DIV>
    <DIV><BR>
    <DIV class=gmail_quote>On Wed, Mar 4, 2009 at 12:02 PM, Matt Campbell <SPAN 
    dir=ltr>&lt;<A href="mailto:mkambol@gmail.com" 
    target=_blank>mkambol@gmail.com</A>&gt;</SPAN> wrote:<BR>
    <BLOCKQUOTE class=gmail_quote 
    style="PADDING-LEFT: 1ex; MARGIN: 0px 0px 0px 0.8ex; BORDER-LEFT: #ccc 1px solid">After 
      syncing to a changelist I was still seeing lots of files in my directories 
      that were showing version 0 in perforce. &nbsp;I eventually got past this 
      by starting from a totally clean slate and syncing.
      <DIV><BR></DIV>
      <DIV>Still investigating, but it looks like changelist&nbsp;11049 is the 
      culprit. &nbsp;The query I posted runs in 2.5 seconds with change 11048, 
      and takes a full minute and a half with 11049.
      <DIV>
      <DIV></DIV>
      <DIV><BR><BR>
      <DIV class=gmail_quote>On Wed, Mar 4, 2009 at 11:16 AM, Julian Hyde <SPAN 
      dir=ltr>&lt;<A href="mailto:jhyde@pentaho.com" 
      target=_blank>jhyde@pentaho.com</A>&gt;</SPAN> wrote:<BR>
      <BLOCKQUOTE class=gmail_quote 
      style="PADDING-LEFT: 1ex; MARGIN: 0px 0px 0px 0.8ex; BORDER-LEFT: #ccc 1px solid">
        <DIV bgcolor="#FFFFFF">
        <DIV>There is no version 0 as such. If p4 sync 'gets' version 0, it 
        removes the file from your sandbox. Is that what you are seeing?
        <DIV>
        <DIV></DIV>
        <DIV><BR><BR>On Mar 4, 2009, at 6:36 AM, Matt Campbell &lt;<A 
        href="mailto:mkambol@gmail.com" target=_blank>mkambol@gmail.com</A>&gt; 
        wrote:<BR><BR></DIV></DIV></DIV>
        <DIV>
        <DIV></DIV>
        <DIV>
        <DIV></DIV>
        <BLOCKQUOTE type="cite">
          <DIV>Hmmm. &nbsp;I see many files in my directories that are marked as 
          having version 0. &nbsp;For example, I see MemberIterCalc.java in my 
          sandbox, even though it was added much after the changelist I synched 
          to. &nbsp;Any ideas how this could happen?<BR><BR>
          <DIV class=gmail_quote>On Wed, Mar 4, 2009 at 9:13 AM, John V. Sichi 
          <SPAN dir=ltr>&lt;<A href="mailto:jsichi@gmail.com" 
          target=_blank></A><A href="mailto:jsichi@gmail.com" 
          target=_blank>jsichi@gmail.com</A>&gt;</SPAN> wrote:<BR>
          <BLOCKQUOTE class=gmail_quote 
          style="PADDING-LEFT: 1ex; MARGIN: 0px 0px 0px 0.8ex; BORDER-LEFT: #ccc 1px solid">
            <DIV>Matt Campbell wrote:<BR>
            <BLOCKQUOTE class=gmail_quote 
            style="PADDING-LEFT: 1ex; MARGIN: 0px 0px 0px 0.8ex; BORDER-LEFT: #ccc 1px solid">I've 
              been trying to isolate when this issue was introduced, but am 
              struggling a bit with perforce. &nbsp;I'm trying to sync to a 
              changelist using something like:<BR><BR>p4 sync 
              //open/mondrian/...@10480<BR><BR>This brings in the set of files 
              from that changelist, but does not appear to delete files from 
              future changelists. &nbsp;<BR>What is the correct way to sync to a 
              changelist?<BR></BLOCKQUOTE><BR></DIV>That is the correct command. 
            &nbsp;It will delete files from future changelists, but it will not 
            delete empty directories unless you have the rmdir option set in 
            your client (the default is normdir).<BR><BR>(Also, use p4 opened to 
            make sure you don't have any files checked out before 
            starting.)<BR><BR>JVS<BR><BR>_______________________________________________<BR>Mondrian 
            mailing list<BR><A href="mailto:Mondrian@pentaho.org" 
            target=_blank></A><A href="mailto:Mondrian@pentaho.org" 
            target=_blank>Mondrian@pentaho.org</A><BR><A 
            href="http://lists.pentaho.org/mailman/listinfo/mondrian" 
            target=_blank></A><A 
            href="http://lists.pentaho.org/mailman/listinfo/mondrian" 
            target=_blank>http://lists.pentaho.org/mailman/listinfo/mondrian</A><BR></BLOCKQUOTE></DIV><BR></DIV></BLOCKQUOTE>
        <BLOCKQUOTE type="cite">
          <DIV><SPAN>_______________________________________________</SPAN><BR><SPAN>Mondrian 
          mailing list</SPAN><BR><SPAN><A href="mailto:Mondrian@pentaho.org" 
          target=_blank>Mondrian@pentaho.org</A></SPAN><BR><SPAN><A 
          href="http://lists.pentaho.org/mailman/listinfo/mondrian" 
          target=_blank>http://lists.pentaho.org/mailman/listinfo/mondrian</A></SPAN><BR></DIV></BLOCKQUOTE></DIV></DIV></DIV><BR>_______________________________________________<BR>Mondrian 
        mailing list<BR><A href="mailto:Mondrian@pentaho.org" 
        target=_blank>Mondrian@pentaho.org</A><BR><A 
        href="http://lists.pentaho.org/mailman/listinfo/mondrian" 
        target=_blank>http://lists.pentaho.org/mailman/listinfo/mondrian</A><BR><BR></BLOCKQUOTE></DIV><BR></DIV></DIV></DIV></BLOCKQUOTE></DIV><BR></DIV></DIV></DIV></DIV></DIV></DIV></BLOCKQUOTE></DIV><BR></BLOCKQUOTE></BODY></HTML>