Vitaliy Serdtsev · Nov 6, 2019 go to post

$EXTRACTdoc

Keep in mind that

Characters are counted from 1.
, so instead

<FONT COLOR="#0000ff">$EXTRACT</FONT><FONT COLOR="#000000">(</FONT><FONT COLOR="#800000">{LabName}</FONT><FONT COLOR="#000000">,0,3)</FONT>

should be

<FONT COLOR="#0000ff">$EXTRACT</FONT><FONT COLOR="#000000">(</FONT><FONT COLOR="#800000">{LabName}</FONT><FONT COLOR="#000000">,1,3)</FONT>

In this case, it is uncritical, because

If the from value is 0 or a negative number, $EXTRACT returns a null string; however, if from is used with to, a from value of 0 or a negative number is treated as a value of 1.
But in other cases it can lead to the wrong result.
Vitaliy Serdtsev · Nov 4, 2019 go to post
That would work storagetime but not at runtime.
It was just a matter of ease of accessing data using SQL. No more than.

Who knows, maybe the author just decided to use SQL to identify duplicates?

I think runtime hook disallowing duplicate inserts would be better.
I agree. But this is a completely different task and is solved in a different way. Like this:
Property Actor As list Of packet.Actor(POPSPEC ".ActorFilter():10") [ Required ];

<FONT COLOR="#000080">Method </FONT><FONT COLOR="#000000">ActorFilter() </FONT><FONT COLOR="#000080">As %Integer </FONT><FONT COLOR="#000000">{   </FONT><FONT COLOR="#0000ff">set </FONT><FONT COLOR="#800000">actorID</FONT><FONT COLOR="#000000">=</FONT><FONT COLOR="#0000ff">$random</FONT><FONT COLOR="#000000">(10)+1

  </FONT><FONT COLOR="#0000ff">for </FONT><FONT COLOR="#800000">i</FONT><FONT COLOR="#000000">=1:1:</FONT><FONT COLOR="#0000ff">$order</FONT><FONT COLOR="#000000">(i%Actor(</FONT><FONT COLOR="#008000">""</FONT><FONT COLOR="#000000">),-1) </FONT><FONT COLOR="#0000ff">return</FONT><FONT COLOR="#000000">:</FONT><FONT COLOR="#800000">actorID</FONT><FONT COLOR="#000000">=</FONT><FONT COLOR="#0000ff">$list</FONT><FONT COLOR="#000000">(i%Actor(</FONT><FONT COLOR="#800000">i</FONT><FONT COLOR="#000000">),1) </FONT><FONT COLOR="#008000">""

  </FONT><FONT COLOR="#0000ff">quit </FONT><FONT COLOR="#800000">actorID </FONT><FONT COLOR="#000000">}</FONT>

The author after all asked about SQL therefore I above and asked to specify that it is necessary actually.

Vitaliy Serdtsev · Nov 4, 2019 go to post

There are a couple of comments:

  1. Instead of
    <FONT COLOR="#000080">Class packet.Actor Extends </FONT><FONT COLOR="#000000">(</FONT><FONT COLOR="#000080">%Persistent</FONT><FONT COLOR="#000000">, </FONT><FONT COLOR="#000080">%Populate</FONT><FONT COLOR="#000000">)
    {
      </FONT><FONT COLOR="#000080">Property </FONT><FONT COLOR="#000000">Name </FONT><FONT COLOR="#000080">As %String </FONT><FONT COLOR="#000000">[ </FONT><FONT COLOR="#000080">Required </FONT><FONT COLOR="#000000">];
    

      </FONT><FONT COLOR="#000080">Index </FONT><FONT COLOR="#000000">NameIndex On Name [ </FONT><FONT COLOR="#000080">Unique </FONT><FONT COLOR="#000000">];

      </FONT><FONT COLOR="#000080">Property </FONT><FONT COLOR="#000000">Age </FONT><FONT COLOR="#000080">As %Integer </FONT><FONT COLOR="#000000">(</FONT><FONT COLOR="#000080">MAXVAL</FONT><FONT COLOR="#000000">=</FONT><FONT COLOR="#000080">100</FONT><FONT COLOR="#000000">, </FONT><FONT COLOR="#000080">MINVAL</FONT><FONT COLOR="#000000">=</FONT><FONT COLOR="#000080">10</FONT><FONT COLOR="#000000">) [ </FONT><FONT COLOR="#000080">Required </FONT><FONT COLOR="#000000">];

      </FONT><FONT COLOR="#000080">Index </FONT><FONT COLOR="#000000">AgeIndex On Age [ </FONT><FONT COLOR="#000080">Unique </FONT><FONT COLOR="#000000">];

      </FONT><FONT COLOR="#000080">Property </FONT><FONT COLOR="#000000">Sex </FONT><FONT COLOR="#000080">As %String </FONT><FONT COLOR="#000000">(</FONT><FONT COLOR="#000080">DISPLAYLIST</FONT><FONT COLOR="#000000">=</FONT><FONT COLOR="#800080">",Woman,Man"</FONT><FONT COLOR="#000000">) [ </FONT><FONT COLOR="#000080">Required </FONT><FONT COLOR="#000000">]; }</FONT>

    better
    Class packet.Actor Extends (%Persistent%Populate)
    {
    
    Index NameIndex On (Name, Age) [ Unique ];
    
    Property Name As %Name Required ];
    
    Property Age As %Integer(MAXVAL 100MINVAL 10) [ Required ];
    
    Property Sex As %String(VALUELIST ",Woman,Man") [ Required ];
    
    }

    Otherwise it will not be possible to insert two or more persons with the same age. Or do you specifically want it?

  2. Property Actor As list of packet.Actor (POPSPEC=".ActorFilter()") [Required];

    This code contradicts the documentation (Specifying the POPSPEC Parameter for List Properties):

    Leave basicspec empty if the property is a list of objects.

    However, in this case, ActorFilter() should return strictly one ID, not a collection.

  3. The data in the Actor property is stored as $lb($lb(ID1),$lb(ID2),..,$lb(IDN)), therefore, to select all records that have ID=6 in this field, you need to perform

    <FONT COLOR="#0000ff">select </FONT><FONT COLOR="#000080">* from </FONT><FONT COLOR="#008000">packet</FONT><FONT COLOR="#000000">.</FONT><FONT COLOR="#008000">Movie </FONT><FONT COLOR="#000080">where </FONT><FONT COLOR="#808000">$listbuild</FONT><FONT COLOR="#000000">(</FONT><FONT COLOR="#008080">'6'</FONT><FONT COLOR="#000000">) %inlist </FONT><FONT COLOR="#008000">Actor</FONT>

It seems to me that in your case it would be easier to do so:

<FONT COLOR="#000080">Property </FONT><FONT COLOR="#000000">Actor </FONT><FONT COLOR="#000080">As list Of packet.Actor</FONT><FONT COLOR="#000000">(</FONT><FONT COLOR="#000080">STORAGEDEFAULT </FONT><FONT COLOR="#000000">= </FONT><FONT COLOR="#800080">"array"</FONT><FONT COLOR="#000000">) [ </FONT><FONT COLOR="#000080">Required </FONT><FONT COLOR="#000000">];</FONT>

Then the query will be simplified:

<FONT COLOR="#0000ff">select </FONT><FONT COLOR="#000080">* from </FONT><FONT COLOR="#008000">packet</FONT><FONT COLOR="#000000">.</FONT><FONT COLOR="#008000">Movie_Actor </FONT><FONT COLOR="#000080">where </FONT><FONT COLOR="#008000">Actor</FONT><FONT COLOR="#000000">=6</FONT>

Or even so

<FONT COLOR="#0000ff">select </FONT><FONT COLOR="#000080">* from </FONT><FONT COLOR="#008000">packet</FONT><FONT COLOR="#000000">.</FONT><FONT COLOR="#008000">Movie </FONT><FONT COLOR="#000080">where </FONT><FONT COLOR="#008000">Movie_Actor</FONT><FONT COLOR="#000000">-></FONT><FONT COLOR="#008000">Actor</FONT><FONT COLOR="#000000">=6</FONT>

Vitaliy Serdtsev · Oct 31, 2019 go to post

Hi, Yana!

Give the class code, the source data and an example of what you want to get in the end.

Vitaliy Serdtsev · Oct 30, 2019 go to post
If we have a lot of votes will consider to add it.
Do we still have to vote for this?

On-my enough one moreover, that moderators (you and Dmitry) and engineers InterSystems (Eduard, Alexander, Anton, Sergey, Anastasia, Timur, etc.) - Russian-speaking.

I have one problem with it - if we introduce Russian Community, will you stop answering questions in English?)
1. I here like writing code more than words. 2. It will depend on who is asking.
Vitaliy Serdtsev · Oct 30, 2019 go to post
  1. Instead of
    Property Product As %String Required ];Property Item As %String CalculatedSqlComputeCode = { {*}=$e({Product},1,5)}, SqlComputed ];

    it is better to use

    Property Product As %String Required ];Property Item As %String(MAXLEN 5) [ RequiredSqlComputeCode = { {*}=$e({Product},1,5)}, SqlComputedSqlComputeOnChange = Product ];
  2. Check on the version 2017.2 can not, but checked on 2018.1
    SELECT * FROM Portal.ProductStats ps left JOIN  Portal.ProductCacheUpdates pcu ON (pcu.Item=ps.ItemWHERE ps.Item=?
    • ExtentSize=1 (Portal.ProductStats) ExtentSize=1000 (Portal.ProductCacheUpdates)

      Relative cost = 1338 ◾Read master map Portal.ProductStats.IDKEY, looping on ID.

      ◾For each row:

      Read index map Portal.ProductCacheUpdates.pcacheUpdsProd, using the given %SQLUPPER(Item), and looping on ID. For each row: Read master map Portal.ProductCacheUpdates.IDKEY, using the given idkey value. Generate a row padded with NULL for table Portal.ProductCacheUpdates if no row qualified. Output the row.

    • ExtentSize=1000 (Portal.ProductStats) ExtentSize=1 (Portal.ProductCacheUpdates)
      Relative cost  = 1219.2
      ◾Read index map Portal.ProductStats.pcacheUpds, using the given %SQLUPPER(Item), and looping on ID.
      

      ◾For each row:

      Read master map Portal.ProductStats.IDKEY, using the given idkey value. Read index map Portal.ProductCacheUpdates.pcacheUpdsProd, using the given %SQLUPPER(Item), and looping on ID. For each row: Read master map Portal.ProductCacheUpdates.IDKEY, using the given idkey value. Generate a row padded with NULL for table Portal.ProductCacheUpdates if no row qualified. Output the row.

      As you can see in both cases the index pcacheUpdsProd is used.

Have you really set up the tables and cleared the cached queries so that the optimizer can start using the new statistics?

Try to do it manually in the terminal:

blablabla><FONT COLOR="#0000ff">d $system</FONT><FONT COLOR="#008080">.SQL</FONT><FONT COLOR="#000000">.</FONT><FONT COLOR="#0000ff">TuneSchema</FONT><FONT COLOR="#000000">(</FONT><FONT COLOR="#008000">"Portal"</FONT><FONT COLOR="#000000">,1), </FONT><FONT COLOR="#0000ff">$SYSTEM</FONT><FONT COLOR="#008080">.SQL</FONT><FONT COLOR="#000000">.</FONT><FONT COLOR="#0000ff">Purge</FONT><FONT COLOR="#000000">(), </FONT><FONT COLOR="#0000ff">$system</FONT><FONT COLOR="#008080">.Status</FONT><FONT COLOR="#000000">.</FONT><FONT COLOR="#0000ff">DisplayError</FONT><FONT COLOR="#000000">(</FONT><FONT COLOR="#0000ff">$system</FONT><FONT COLOR="#008080">.OBJ</FONT><FONT COLOR="#000000">.</FONT><FONT COLOR="#0000ff">CompilePackage</FONT><FONT COLOR="#000000">(</FONT><FONT COLOR="#008000">"Portal"</FONT><FONT COLOR="#000000">,</FONT><FONT COLOR="#008000">"cu-d"</FONT><FONT COLOR="#000000">))</FONT>
Vitaliy Serdtsev · Oct 30, 2019 go to post

The documentation describes in detail how and why.

For example, sometimes the optimizer decides not to use the index if a full crawl would be more efficient. It depends on many parameters: ExtentSize, Selectivity, etc.

Give here what Robert asks, and it will be possible to tell more precisely why.

Vitaliy Serdtsev · Oct 30, 2019 go to post

Try this:

<FONT COLOR="#0000ff">update </FONT><FONT COLOR="#008000">RB_ResEffDateSessPayorRestr </FONT><FONT COLOR="#000080">set </FONT><FONT COLOR="#008000">RESTR_DATETo</FONT><FONT COLOR="#000000">=</FONT><FONT COLOR="#808000">to_date</FONT><FONT COLOR="#000000">(</FONT><FONT COLOR="#808000">DATEADD</FONT><FONT COLOR="#000000">(</FONT><FONT COLOR="#008080">'year'</FONT><FONT COLOR="#000000">,1,</FONT><FONT COLOR="#008000">RESTR_DATETo</FONT><FONT COLOR="#000000">),</FONT><FONT COLOR="#008080">'YYYY-MM-DD'</FONT><FONT COLOR="#000000">) </FONT><FONT COLOR="#000080">where </FONT><FONT COLOR="#008000">YEAR</FONT><FONT COLOR="#000000">(</FONT><FONT COLOR="#008000">RESTR_DATETo</FONT><FONT COLOR="#000000">)=2020</FONT>
Or this:
<FONT COLOR="#0000ff">update </FONT><FONT COLOR="#008000">RB_ResEffDateSessPayorRestr </FONT><FONT COLOR="#000080">set </FONT><FONT COLOR="#008000">RESTR_DATETo</FONT><FONT COLOR="#000000">=%odbcin(</FONT><FONT COLOR="#808000">DATEADD</FONT><FONT COLOR="#000000">(</FONT><FONT COLOR="#008080">'year'</FONT><FONT COLOR="#000000">,1,</FONT><FONT COLOR="#008000">RESTR_DATETo</FONT><FONT COLOR="#000000">)) </FONT><FONT COLOR="#000080">where </FONT><FONT COLOR="#008000">YEAR</FONT><FONT COLOR="#000000">(</FONT><FONT COLOR="#008000">RESTR_DATETo</FONT><FONT COLOR="#000000">)=2020</FONT>
Vitaliy Serdtsev · Oct 7, 2019 go to post

<FONT COLOR="#800080">&SQL(</FONT><FONT COLOR="#0000ff">SELECT </FONT><FONT COLOR="#008000">ID </FONT><FONT COLOR="#000080">FROM </FONT><FONT COLOR="#008000">Cinema</FONT><FONT COLOR="#000000">.</FONT><FONT COLOR="#008000">Film </FONT><FONT COLOR="#000080">ORDER BY </FONT><FONT COLOR="#008000">ID </FONT><FONT COLOR="#000080">DESC</FONT><FONT COLOR="#800080">)</FONT>

similar to the query

<FONT COLOR="#800080">&SQL(</FONT><FONT COLOR="#0000ff">SELECT </FONT><FONT COLOR="#000080">TOP ALL </FONT><FONT COLOR="#008000">ID </FONT><FONT COLOR="#000080">FROM </FONT><FONT COLOR="#008000">Cinema</FONT><FONT COLOR="#000000">.</FONT><FONT COLOR="#008000">Film </FONT><FONT COLOR="#000080">ORDER BY </FONT><FONT COLOR="#008000">ID </FONT><FONT COLOR="#000080">DESC</FONT><FONT COLOR="#800080">)</FONT>


Therefore, it is natural that the query plans

<FONT COLOR="#800080">&SQL(</FONT><FONT COLOR="#0000ff">SELECT </FONT><FONT COLOR="#000080">TOP ALL </FONT><FONT COLOR="#008000">ID </FONT><FONT COLOR="#000080">FROM </FONT><FONT COLOR="#008000">Cinema</FONT><FONT COLOR="#000000">.</FONT><FONT COLOR="#008000">Film </FONT><FONT COLOR="#000080">ORDER BY </FONT><FONT COLOR="#008000">ID </FONT><FONT COLOR="#000080">DESC</FONT><FONT COLOR="#800080">)</FONT> and <FONT COLOR="#800080">&SQL(</FONT><FONT COLOR="#0000ff">SELECT </FONT><FONT COLOR="#000080">TOP 1 </FONT><FONT COLOR="#008000">ID </FONT><FONT COLOR="#000080">FROM </FONT><FONT COLOR="#008000">Cinema</FONT><FONT COLOR="#000000">.</FONT><FONT COLOR="#008000">Film </FONT><FONT COLOR="#000080">ORDER BY </FONT><FONT COLOR="#008000">ID </FONT><FONT COLOR="#000080">DESC</FONT><FONT COLOR="#800080">)</FONT>

are so significantly different.

Vitaliy Serdtsev · Sep 23, 2019 go to post
Class dc.test Extends %RegisteredObject
{

ClassMethod Run(
  a,
  b)
{
  w $$$FormatText("a=%1, b=%2",$g(a,"<null>"),$g(b,"<null>")),!
}

ClassMethod Test()
{
  cName="dc.test",
    mName="Run",

    args=2,
    args(1)="2019-01-01",
    args(2)="1,2,3,4"
    
  d $classmethod(cName,mName,args...)
  
  args
  args=1,
    args(1)=77
  d $classmethod(cName,mName,args...)

  args
  args=2,
    args(2)=33
  d $classmethod(cName,mName,args...)

  args
  args=""
  d $classmethod(cName,mName,args...)
}

}

Result:

USER>##class(dc.test).Test()
a=2019-01-01, b=1,2,3,4
a=77, b=<null>
a=<null>, b=33
a=<null>, b=<null>
Vitaliy Serdtsev · Sep 18, 2019 go to post

The field TimeCreated is of type Ens.DataType.UTC.

Then so:

<FONT COLOR="#808000">datepart</FONT><FONT COLOR="#000000">(</FONT><FONT COLOR="#008080">'hh'</FONT><FONT COLOR="#000000">, %external(</FONT><FONT COLOR="#008000">TimeCreated</FONT><FONT COLOR="#000000">))

See Data Display Options

Vitaliy Serdtsev · Sep 17, 2019 go to post

At me in SMP the following query returns 23:

<FONT COLOR="#0000ff">select </FONT><FONT COLOR="#808000">datepart</FONT><FONT COLOR="#000000">(</FONT><FONT COLOR="#008080">'hh'</FONT><FONT COLOR="#000000">, {</FONT><FONT COLOR="#000080">ts </FONT><FONT COLOR="#008080">'2019-09-10 23:01:45'</FONT><FONT COLOR="#000000">})</FONT>
Vitaliy Serdtsev · Jul 30, 2019 go to post

By default, the mac address of the computer on which the DBMS instance is running is returned. But you can get the mac address of any other computer, see getmac /?.

Vitaliy Serdtsev · Jul 29, 2019 go to post

I checked for versions 2009.1/2010.1: unfortunately, the <FONT COLOR="#0000ff">$zu</FONT><FONT COLOR="#000000">(114,0)</FONT> returns nothing, therefore, remains variant with the command line.

Example for Windows, provided that the system has a single network card:

<FONT COLOR="#0000ff">#include </FONT><FONT COLOR="#000000">%syConfig
 </FONT><FONT COLOR="#0000ff">n </FONT><FONT COLOR="#800000">result
 </FONT><FONT COLOR="#0000ff">w $zu</FONT><FONT COLOR="#000000">(144,1,</FONT><FONT COLOR="#0000ff">$$$DEFETHADDR</FONT><FONT COLOR="#000000">),!,</FONT><FONT COLOR="#008000">"------"</FONT><FONT COLOR="#000000">,!
 
 </FONT><FONT COLOR="#0000ff">d $system</FONT><FONT COLOR="#008080">.OBJ</FONT><FONT COLOR="#000000">.</FONT><FONT COLOR="#0000ff">DisplayError</FONT><FONT COLOR="#000000">(</FONT><FONT COLOR="#000080">##class</FONT><FONT COLOR="#000000">(</FONT><FONT COLOR="#008080">%Net.Remote.Utility</FONT><FONT COLOR="#000000">).</FONT><FONT COLOR="#0000ff">RunCommandViaCPIPE</FONT><FONT COLOR="#000000">(</FONT><FONT COLOR="#008000">"getmac /NH /fo table"</FONT><FONT COLOR="#000000">,,.</FONT><FONT COLOR="#800000">result</FONT><FONT COLOR="#000000">))
 </FONT><FONT COLOR="#0000ff">w $p</FONT><FONT COLOR="#000000">(</FONT><FONT COLOR="#800000">result</FONT><FONT COLOR="#000000">,</FONT><FONT COLOR="#008000">" "</FONT><FONT COLOR="#000000">,1)</FONT>
PS: for other OS command line may be different.
Vitaliy Serdtsev · Jul 25, 2019 go to post

Try this:

<FONT COLOR="#0000ff">w $zu</FONT><FONT COLOR="#000000">(114,0)</FONT>

or

<FONT COLOR="#0000ff">w $$$DEFETHADDR </FONT><FONT COLOR="#008000">; from %syConfig.inc</FONT>

Vitaliy Serdtsev · Jul 24, 2019 go to post

Important note: it should be noted that the proposed solutions refer only to the port of the private web server, which may not even be installed. In the case of an external web server, this is not possible.

Vitaliy Serdtsev · Jul 24, 2019 go to post

Thank you for your comment. This code is taken from the source code %SYS, which in theory should be an example for application developers.

I hope that InterSystems developers will see your comment and make appropriate changes.

Vitaliy Serdtsev · Jul 16, 2019 go to post

Intel i5-2400

10000 digits ~ 58 sec.

calcPI(n) public { 
  s $lb(len,nines,predigit,r)=$lb(10*n\3,0,0,"")
  
  i=1:1:len a(i)=2
  
  j=1:1:{
    q=0
    i=len:-1:1 x=10*a(i)+(q*i), a(i)=x#(2*i-1), q=x\(2*i-1)
    a(1)=q#10, q=q\10
    q=9 {
      nines=nines+1
    }elseif q=10 {
      r=r_(predigit+1)_$$repeat^%qarfunc(0,nines), predigit=0, nines=0
    }else{
      r=r_predigitpredigit=q
      s:nines r=r_$$repeat^%qarfunc(9,nines), nines=0
    }
  }
  r_predigit
}
Vitaliy Serdtsev · Jul 12, 2019 go to post

And if so?

<FONT COLOR="#0000ff">w $zobjref</FONT><FONT COLOR="#000000">(^||PPG(1)).</FONT><FONT COLOR="#0000ff">Name</FONT>

Still take a look at <FONT COLOR="#0000ff">$$$objOrefToInt</FONT>/<FONT COLOR="#0000ff">$$$objIntToOref</FONT> (%occObject.inc)

PS: it should be noted that OREF ≠ OID and serve different purposes.

Vitaliy Serdtsev · Jul 10, 2019 go to post

I found out the reason for the difference in the result BASIC256:

Instead

len = 10*n\4,

must be

len = 10*n\3,

Error on site.

Vitaliy Serdtsev · Jul 10, 2019 go to post

Translation of: LUA

<FONT COLOR="#ff0000">calcPILua</FONT><FONT COLOR="#000000">(n=1000) </FONT><FONT COLOR="#0000ff">public </FONT><FONT COLOR="#800080">{ 
  </FONT><FONT COLOR="#0000ff">s </FONT><FONT COLOR="#800000">len </FONT><FONT COLOR="#000000">= 10*</FONT><FONT COLOR="#800000">n</FONT><FONT COLOR="#000000">\3,
    </FONT><FONT COLOR="#800000">nines </FONT><FONT COLOR="#000000">= 0,
    </FONT><FONT COLOR="#800000">predigit </FONT><FONT COLOR="#000000">= 0
  
  </FONT><FONT COLOR="#0000ff">f </FONT><FONT COLOR="#800000">j</FONT><FONT COLOR="#000000">=1:1:</FONT><FONT COLOR="#800000">len </FONT><FONT COLOR="#0000ff">s </FONT><FONT COLOR="#800000">a</FONT><FONT COLOR="#000000">(</FONT><FONT COLOR="#800000">j</FONT><FONT COLOR="#000000">)=2
  
  </FONT><FONT COLOR="#0000ff">f </FONT><FONT COLOR="#800000">j</FONT><FONT COLOR="#000000">=1:1:</FONT><FONT COLOR="#800000">n </FONT><FONT COLOR="#800080">{
    </FONT><FONT COLOR="#0000ff">s </FONT><FONT COLOR="#800000">q</FONT><FONT COLOR="#000000">=0
    </FONT><FONT COLOR="#0000ff">f </FONT><FONT COLOR="#800000">i</FONT><FONT COLOR="#000000">=</FONT><FONT COLOR="#800000">len</FONT><FONT COLOR="#000000">:-1:1 </FONT><FONT COLOR="#800080">{
      </FONT><FONT COLOR="#0000ff">s </FONT><FONT COLOR="#800000">x </FONT><FONT COLOR="#000000">= 10*</FONT><FONT COLOR="#800000">a</FONT><FONT COLOR="#000000">(</FONT><FONT COLOR="#800000">i</FONT><FONT COLOR="#000000">) + (</FONT><FONT COLOR="#800000">q</FONT><FONT COLOR="#000000"></FONT><FONT COLOR="#800000">i</FONT><FONT COLOR="#000000">),
        </FONT><FONT COLOR="#800000">a</FONT><FONT COLOR="#000000">(</FONT><FONT COLOR="#800000">i</FONT><FONT COLOR="#000000">)=</FONT><FONT COLOR="#800000">x</FONT><FONT COLOR="#000000">#(2</FONT><FONT COLOR="#800000">i</FONT><FONT COLOR="#000000">-1),
        </FONT><FONT COLOR="#800000">q</FONT><FONT COLOR="#000000">=</FONT><FONT COLOR="#800000">x</FONT><FONT COLOR="#000000">(2*</FONT><FONT COLOR="#800000">i</FONT><FONT COLOR="#000000">-1)
    </FONT><FONT COLOR="#800080">}
    </FONT><FONT COLOR="#0000ff">s </FONT><FONT COLOR="#800000">a</FONT><FONT COLOR="#000000">(1)=</FONT><FONT COLOR="#800000">q</FONT><FONT COLOR="#000000">#10,
      </FONT><FONT COLOR="#800000">q</FONT><FONT COLOR="#000000">=</FONT><FONT COLOR="#800000">q</FONT><FONT COLOR="#000000">\10
    </FONT><FONT COLOR="#0000ff">i </FONT><FONT COLOR="#800000">q</FONT><FONT COLOR="#000000">=9 </FONT><FONT COLOR="#800080">{
      </FONT><FONT COLOR="#0000ff">s </FONT><FONT COLOR="#800000">nines </FONT><FONT COLOR="#000000">= </FONT><FONT COLOR="#800000">nines </FONT><FONT COLOR="#000000">+ 1
    </FONT><FONT COLOR="#800080">}</FONT><FONT COLOR="#0000ff">elseif </FONT><FONT COLOR="#800000">q</FONT><FONT COLOR="#000000">=10 </FONT><FONT COLOR="#800080">{
      </FONT><FONT COLOR="#0000ff">w </FONT><FONT COLOR="#800000">predigit</FONT><FONT COLOR="#000000">+1
      </FONT><FONT COLOR="#0000ff">f </FONT><FONT COLOR="#800000">k </FONT><FONT COLOR="#000000">= 1:1:</FONT><FONT COLOR="#800000">nines </FONT><FONT COLOR="#0000ff">w </FONT><FONT COLOR="#000000">0
      </FONT><FONT COLOR="#0000ff">s </FONT><FONT COLOR="#800000">predigit </FONT><FONT COLOR="#000000">= 0, </FONT><FONT COLOR="#800000">nines </FONT><FONT COLOR="#000000">= 0
    </FONT><FONT COLOR="#800080">}</FONT><FONT COLOR="#0000ff">else</FONT><FONT COLOR="#800080">{
      </FONT><FONT COLOR="#0000ff">w </FONT><FONT COLOR="#800000">predigit
      </FONT><FONT COLOR="#0000ff">s </FONT><FONT COLOR="#800000">predigit </FONT><FONT COLOR="#000000">= </FONT><FONT COLOR="#800000">q
      </FONT><FONT COLOR="#0000ff">i </FONT><FONT COLOR="#800000">nines </FONT><FONT COLOR="#800080">{
        </FONT><FONT COLOR="#0000ff">f </FONT><FONT COLOR="#800000">k </FONT><FONT COLOR="#000000">= 1:1:</FONT><FONT COLOR="#800000">nines </FONT><FONT COLOR="#0000ff">w </FONT><FONT COLOR="#000000">9
        </FONT><FONT COLOR="#0000ff">s </FONT><FONT COLOR="#800000">nines </FONT><FONT COLOR="#000000">= 0
      </FONT><FONT COLOR="#800080">}
    }
  }
  </FONT><FONT COLOR="#0000ff">w </FONT><FONT COLOR="#800000">predigit
</FONT><FONT COLOR="#800080">}</FONT>
The result of this example is exactly the same as the result of the program C# (tested at n=10000).
Vitaliy Serdtsev · Jul 10, 2019 go to post

Translation of: BASIC256

<FONT COLOR="#ff0000">calcPI</FONT><FONT COLOR="#000000">(n=1000) </FONT><FONT COLOR="#0000ff">public </FONT><FONT COLOR="#800080">{ 
  </FONT><FONT COLOR="#0000ff">s </FONT><FONT COLOR="#800000">len </FONT><FONT COLOR="#000000">= 10*</FONT><FONT COLOR="#800000">n</FONT><FONT COLOR="#000000">\4,
    </FONT><FONT COLOR="#800000">needdecimal </FONT><FONT COLOR="#000000">= </FONT><FONT COLOR="#0000ff">$$$YES</FONT><FONT COLOR="#000000">,
    </FONT><FONT COLOR="#800000">nines </FONT><FONT COLOR="#000000">= 0,
    </FONT><FONT COLOR="#800000">predigit </FONT><FONT COLOR="#000000">= 0  </FONT><FONT COLOR="#008000">;# {First predigit is a 0}
   
  </FONT><FONT COLOR="#0000ff">f </FONT><FONT COLOR="#800000">j</FONT><FONT COLOR="#000000">=1:1:</FONT><FONT COLOR="#800000">len </FONT><FONT COLOR="#0000ff">s </FONT><FONT COLOR="#800000">a</FONT><FONT COLOR="#000000">(</FONT><FONT COLOR="#800000">j</FONT><FONT COLOR="#000000">-1)=2 </FONT><FONT COLOR="#008000">;# {Start with 2s}
  
  </FONT><FONT COLOR="#0000ff">f </FONT><FONT COLOR="#800000">j</FONT><FONT COLOR="#000000">=1:1:</FONT><FONT COLOR="#800000">n </FONT><FONT COLOR="#800080">{
    </FONT><FONT COLOR="#0000ff">s </FONT><FONT COLOR="#800000">q</FONT><FONT COLOR="#000000">=0
    </FONT><FONT COLOR="#0000ff">f </FONT><FONT COLOR="#800000">i</FONT><FONT COLOR="#000000">=</FONT><FONT COLOR="#800000">len</FONT><FONT COLOR="#000000">:-1:1 </FONT><FONT COLOR="#800080">{
      </FONT><FONT COLOR="#008000">;#  {Work backwards}
      </FONT><FONT COLOR="#0000ff">s </FONT><FONT COLOR="#800000">x </FONT><FONT COLOR="#000000">= 10*</FONT><FONT COLOR="#800000">a</FONT><FONT COLOR="#000000">(</FONT><FONT COLOR="#800000">i</FONT><FONT COLOR="#000000">-1) + (</FONT><FONT COLOR="#800000">q</FONT><FONT COLOR="#000000"></FONT><FONT COLOR="#800000">i</FONT><FONT COLOR="#000000">),
        </FONT><FONT COLOR="#800000">a</FONT><FONT COLOR="#000000">(</FONT><FONT COLOR="#800000">i</FONT><FONT COLOR="#000000">-1)=</FONT><FONT COLOR="#800000">x</FONT><FONT COLOR="#000000">#(2</FONT><FONT COLOR="#800000">i</FONT><FONT COLOR="#000000">-1),
        </FONT><FONT COLOR="#800000">q</FONT><FONT COLOR="#000000">=</FONT><FONT COLOR="#800000">x</FONT><FONT COLOR="#000000">(2*</FONT><FONT COLOR="#800000">i</FONT><FONT COLOR="#000000">-1)
    </FONT><FONT COLOR="#800080">}
    </FONT><FONT COLOR="#0000ff">s </FONT><FONT COLOR="#800000">a</FONT><FONT COLOR="#000000">(0)=</FONT><FONT COLOR="#800000">q</FONT><FONT COLOR="#000000">#10,
      </FONT><FONT COLOR="#800000">q</FONT><FONT COLOR="#000000">=</FONT><FONT COLOR="#800000">q</FONT><FONT COLOR="#000000">\10
    </FONT><FONT COLOR="#0000ff">i </FONT><FONT COLOR="#800000">q</FONT><FONT COLOR="#000000">=9 </FONT><FONT COLOR="#800080">{
      </FONT><FONT COLOR="#0000ff">s </FONT><FONT COLOR="#800000">nines </FONT><FONT COLOR="#000000">= </FONT><FONT COLOR="#800000">nines </FONT><FONT COLOR="#000000">+ 1
    </FONT><FONT COLOR="#800080">}</FONT><FONT COLOR="#0000ff">elseif </FONT><FONT COLOR="#800000">q</FONT><FONT COLOR="#000000">=10 </FONT><FONT COLOR="#800080">{
      </FONT><FONT COLOR="#0000ff">s </FONT><FONT COLOR="#800000">d </FONT><FONT COLOR="#000000">= </FONT><FONT COLOR="#800000">predigit</FONT><FONT COLOR="#000000">+1 </FONT><FONT COLOR="#0000ff">d </FONT><FONT COLOR="#ff0000">outputd
      </FONT><FONT COLOR="#0000ff">i </FONT><FONT COLOR="#800000">nines</FONT><FONT COLOR="#000000">>0 </FONT><FONT COLOR="#0000ff">f </FONT><FONT COLOR="#800000">k </FONT><FONT COLOR="#000000">= 1:1:</FONT><FONT COLOR="#800000">nines </FONT><FONT COLOR="#0000ff">s </FONT><FONT COLOR="#800000">d </FONT><FONT COLOR="#000000">=  0 </FONT><FONT COLOR="#0000ff">d </FONT><FONT COLOR="#ff0000">outputd
      </FONT><FONT COLOR="#0000ff">s </FONT><FONT COLOR="#800000">predigit </FONT><FONT COLOR="#000000">= 0, </FONT><FONT COLOR="#800000">nines </FONT><FONT COLOR="#000000">= 0
    </FONT><FONT COLOR="#800080">}</FONT><FONT COLOR="#0000ff">else</FONT><FONT COLOR="#800080">{
      </FONT><FONT COLOR="#0000ff">s </FONT><FONT COLOR="#800000">d </FONT><FONT COLOR="#000000">= </FONT><FONT COLOR="#800000">predigit</FONT><FONT COLOR="#000000">,</FONT><FONT COLOR="#800000">predigit </FONT><FONT COLOR="#000000">= </FONT><FONT COLOR="#800000">q </FONT><FONT COLOR="#0000ff">d </FONT><FONT COLOR="#ff0000">outputd
      </FONT><FONT COLOR="#0000ff">i </FONT><FONT COLOR="#800000">nines </FONT><FONT COLOR="#800080">{
        </FONT><FONT COLOR="#0000ff">f </FONT><FONT COLOR="#800000">k </FONT><FONT COLOR="#000000">= 1:1:</FONT><FONT COLOR="#800000">nines </FONT><FONT COLOR="#0000ff">s </FONT><FONT COLOR="#800000">d </FONT><FONT COLOR="#000000">= 9 </FONT><FONT COLOR="#0000ff">d </FONT><FONT COLOR="#ff0000">outputd
        </FONT><FONT COLOR="#0000ff">s </FONT><FONT COLOR="#800000">nines </FONT><FONT COLOR="#000000">= 0
      </FONT><FONT COLOR="#800080">}
    }
  }
  </FONT><FONT COLOR="#0000ff">w </FONT><FONT COLOR="#800000">predigit
  </FONT><FONT COLOR="#0000ff">q
   
</FONT><FONT COLOR="#ff0000">outputd</FONT><FONT COLOR="#000000">()
  </FONT><FONT COLOR="#0000ff">if </FONT><FONT COLOR="#800000">needdecimal </FONT><FONT COLOR="#800080">{
     </FONT><FONT COLOR="#0000ff">q</FONT><FONT COLOR="#000000">:</FONT><FONT COLOR="#800000">d</FONT><FONT COLOR="#000000">=0
     </FONT><FONT COLOR="#0000ff">w </FONT><FONT COLOR="#800000">d</FONT><FONT COLOR="#000000">_</FONT><FONT COLOR="#008000">"."
     </FONT><FONT COLOR="#0000ff">s </FONT><FONT COLOR="#800000">needdecimal </FONT><FONT COLOR="#000000">= </FONT><FONT COLOR="#0000ff">$$$NO
  </FONT><FONT COLOR="#800080">} </FONT><FONT COLOR="#0000ff">else </FONT><FONT COLOR="#800080">{
     </FONT><FONT COLOR="#0000ff">w </FONT><FONT COLOR="#800000">d
  </FONT><FONT COLOR="#800080">}
}</FONT>
The greater "n", the higher the accuracy.

If there is a lack of RAM, you can easily replace the local array "a" with globals ^||a or ^a.

Vitaliy Serdtsev · Jun 27, 2019 go to post
  w $$MyFunc(1),!,
    $$MyFunc(1,.V)," V=",V,!

MyFunc(p...)
  Answer=p_" params"
  s:p=2 p(2)="it's all good"
  Answer


USER>do ^test
1 params
2 params V=it's all good