Inner Product: Difference between revisions

Jump to navigation Jump to search
2,422 bytes added ,  11:47, 26 January 2022
Line 117: Line 117:
== Differences between dialects ==
== Differences between dialects ==
Implementations differ on the exact behaviour of inner product when the right operand is not a [[scalar function]]. It follows from page 121 of the ISO/IEC 13751:2001(E) [[standard]] specifies that <source lang=apl inline>X f.g Y</source> is equivalent to <source lang=apl inline>⊃⍤0 f/¨ (⊂[⍴⍴x]x)∘.g ⊂[1]y</source>. This is indeed what [[APL2]], [[APLX]], and [[ngn/apl]] follow, while [[Dyalog APL]] and [[GNU APL]] use <source lang=apl inline>⊃⍤0 f/¨ (⊂[⍴⍴x]x)∘.(g¨) ⊂[1]y</source>.
Implementations differ on the exact behaviour of inner product when the right operand is not a [[scalar function]]. It follows from page 121 of the ISO/IEC 13751:2001(E) [[standard]] specifies that <source lang=apl inline>X f.g Y</source> is equivalent to <source lang=apl inline>⊃⍤0 f/¨ (⊂[⍴⍴x]x)∘.g ⊂[1]y</source>. This is indeed what [[APL2]], [[APLX]], and [[ngn/apl]] follow, while [[Dyalog APL]] and [[GNU APL]] use <source lang=apl inline>⊃⍤0 f/¨ (⊂[⍴⍴x]x)∘.(g¨) ⊂[1]y</source>.
== Model ==
[[Roger Hui]] writes:<ref>[[Roger Hui]]. ''inner product''. Internal Dyalog email. 24 July 2020.</ref>
<blockquote>
The following dop models inner product in Dyalog APL, with caveats.  If you find a case where <source lang=apl inline>f.g</source> differs from <source lang=apl inline>f IP g</source>, not covered by the caveats, I'd be interested.
<source lang=apl>
IP←{                               
  assert((⊃⌽⍴⍺)≡≢⍵)∨(1=×/⍴⍺)∨1=×/⍴⍵:
  ⊃⍤0 ⊢ (↓⍺) ∘.(⍺⍺/⍵⍵¨) ↓(¯1⌽⍳⍴⍴⍵)⍉⍵   
}
assert←{⍺←'assertion failure' ⋄ 0∊⍵:⍺ ⎕SIGNAL 8 ⋄ shy←0}
</source>
(Explanation: What's with the <source lang=apl inline>⊃⍤0</source> in <source lang=apl inline>IP</source>?  It's because <source lang=apl inline>∘.f</source> has an implicit each, applying <source lang=apl inline>⊂</source> to each item of its result.  But the <source lang=apl inline>⍺⍺/</source> in <source lang=apl inline>(⍺⍺/⍵⍵¨)</source> also has an implicit each.  So the <source lang=apl inline>⊃⍤0</source> gets rid of one of those encloses.)
Caveats:
* You can not use the hybrid <source lang=apl inline>/</source> directly as an operand as it runs afoul of the parser in weird and wonderful ways.  Instead, you have to use <source lang=apl inline>{⍺/⍵}</source>.  The same goes for <source lang=apl inline>\</source> and <source lang=apl inline>{⍺\⍵}</source> I guess.
* It differs from ISO/IEC 13751:2001(E) in using <source lang=apl inline>⍵⍵¨</source> instead of just <source lang=apl inline>⍵⍵</source> in the central key expression (i.e. <source lang=apl inline>(⍺⍺/⍵⍵¨)</source> instead of <source lang=apl inline>(⍺⍺/⍵⍵)</source>).  So does the primitive <source lang=apl inline>f.g</source>.
* It differs from ISO/IEC 13751:2001(E) in doing full-blown single extension instead of just scalar and 1-element vector extension (as in APL2).  So does the primitive <source lang=apl inline>f.g</source>.  e.g.<source lang=apl>
  (3 4⍴5)+.×1 1 1 1⍴6  ⍝ works in Dyalog, not in ISO or APL2</source>
* It differs from NARS2000 or APL\360 in not permitting unit axis extension. So does the primitive <source lang=apl inline>f.g</source>.  e.g.<source lang=apl>
  (3 4⍴5)+.×1 5⍴6  ⍝ works in NARS2000 or APL\360, not in Dyalog APL</source>
</blockquote>


== External links ==
== External links ==
Line 125: Line 151:
* [https://microapl.com/apl_help/ch_020_020_880.htm APLX]
* [https://microapl.com/apl_help/ch_020_020_880.htm APLX]
* J [https://www.jsoftware.com/help/dictionary/d300.htm Dictionary], [https://code.jsoftware.com/wiki/Vocabulary/dot#dyadic NuVoc]
* J [https://www.jsoftware.com/help/dictionary/d300.htm Dictionary], [https://code.jsoftware.com/wiki/Vocabulary/dot#dyadic NuVoc]
 
== References ==
<references/>
{{APL built-ins}}[[Category:Primitive operators]]
{{APL built-ins}}[[Category:Primitive operators]]

Navigation menu