Re: [swift-users] Incorrect Fisher-Yates shuffle in example code

2017-12-17 Thread Dave Abrahams via swift-users


> On Dec 16, 2017, at 4:34 PM, Nevin Brackett-Rozinsky via swift-users 
>  wrote:
> 
> public extension MutableCollection where Self: RandomAccessCollection, 
> IndexDistance == Int {
> 

IndexDistance == Int is an over-constraint, FWIW.  Adding it is generally a 
mistake.  Not a serious one, but it does limit utility somewhat.

HTH,
Dave
___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] Compiler fLag to activate SE-0143 (conditional conformance)?

2017-12-14 Thread Dave Abrahams via swift-users


> On Dec 14, 2017, at 1:08 PM, Slava Pestov via swift-users 
>  wrote:
> 
> 
> 
>> On Dec 14, 2017, at 10:56 AM, torquato via swift-users 
>>  wrote:
>> 
>> 
>> SE-0143 has been accepted, but is not activated by default in the last 
>> builds. As per Snapshot 2017-12-06 I get the Error message: "Conditional 
>> conformance of 'Array' to 'Foo' depends on an experimental feature 
>> (SE-0143)".
>> Somewhere on the dev list archives I've read about a compiler flag that 
>> activates this feature. I can't find it anymore. Bad Google-Fu.
>> 
>> Questions:
>> 
>> 1.)
>> What is this compiler flag?
> 
> -enable-experimental-conditional-conformances
> 
>> 
>> 2.)
>> Shouldn't this (flag) be mentioned in the proposal? Or the Generics 
>> Manifesto? Somewhere? At least for the meantime…?
> 
> I think until the flag is gone the proposal does not count as “implemented”.

IMO it makes as much sense to mention the flag in the proposal as it does to 
point at a proof-of-concept implementation that accompanies a proposal.  
Generally we only accept proposals that “have an implementation” these days.  

> 
>> 
>> 3.)
>> What is the _real_ status of this proposal? Is it really accepted and going 
>> into a next release or is this just a tryout that can be dropped any time?
> 
> It’s almost all implemented, except for dynamic casts to protocols that are 
> conditionally conformed to. This part didn’t get finished before the 4.1 
> branch date so we put in the flag.
> 
> Slava
> 
>> 
>> ___
>> swift-users mailing list
>> swift-users@swift.org
>> https://lists.swift.org/mailman/listinfo/swift-users
> 
> ___
> swift-users mailing list
> swift-users@swift.org
> https://lists.swift.org/mailman/listinfo/swift-users


FWIW-ly,

—
-Dave





___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] Exceptional values in the Comparable protocol

2017-07-11 Thread Dave Abrahams via swift-users

on Tue Jul 11 2017, Martin R  wrote:

> Thank you for the clarification!

Sure, happy to help!

-- 
-Dave
___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] Exceptional values in the Comparable protocol

2017-07-10 Thread Dave Abrahams via swift-users

on Sun Jul 09 2017, Martin R  wrote:

> The Comparable protocol requires that < and == impose a strict total
> order: exactly one of a==b, ab must hold for all values a and b
> of a conforming type.
>
> But it is also noted that a conforming type may contain a subset of
> „exceptional values“ which do not take part in the strict total order
> (such as FloatingPoint.nan).
>
> What does that mean for functions taking comparable arguments, e.g.
>
> func mySuperSort(a: inout [T]) { }
>
> Can the function implementation assume that all values passed to it
> take part in the strict total order? In other words: „exceptional
> values“ must not be passed to the function?

Yes

> Or must the function take that case into account and must not assume
> that exactly one of a==b, a a>b holds for any arguments passed to it?

It need not, but it may do so as a matter of QOI (Quality Of
Implementation).  It is a good idea to make such a function work for NaN
if you can figure out what the semantics should be and it doesn't overly
impact the performance of other important use cases.

Hope this helps,

-- 
-Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] Design guidelines for computed property vs no-arg method

2017-07-06 Thread Dave Abrahams via swift-users

on Wed Jul 05 2017, Jens Persson  wrote:

> On Wed, Jul 5, 2017 at 11:50 PM, Dave Abrahams via swift-users <
> swift-users@swift.org> wrote:
>
>> …
>> As a name, signum falls into the “term-of-art” category, so at least
>> that part is in conformance to the guidelines.  In specialized areas
>> like this one, I generally defer to the domain experts, and IIRC our
>> numerics people thought a function was more appropriate.  In general,
>> though, we were unable to come up with solid guidelines for the use of
>> properties vs. functions.  You can read more about this in the thread
>> that starts here:
>> https://lists.swift.org/pipermail/swift-evolution/
>> Week-of-Mon-20160125/007927.html
>>
>>
> Thanks, I'll read that thread.
> I am however noting that FloatingPoint.sign is a computed property.
> Seems to me like the "term-of-art" category is a rather fussy and
> complicated/complicating concept.

I understand.  Unfortunately it is necessary unless we are going—for
example—to start spelling out sine(x) and cosine(x), which would not be
acceptable to important constituencies of the language.

-- 
-Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] Associatedtype Naming Conventions

2017-06-06 Thread Dave Abrahams via swift-users

on Tue Jun 06 2017, Karl Wagner  wrote:

>> On 7. Jun 2017, at 00:25, Dave Abrahams via swift-users 
>> <swift-users@swift.org> wrote:
>> 
>> 
>> on Wed May 31 2017, Steven Brunwasser  <http://swift-users-at-swift.org/>> wrote:
>> 
>
>>> Yes, I understand this. I was just wondering if there was a naming
>>> convention I should use to differentiate them.
>> 
>> I would try to find something more specific and descriptive than
>> “Container” and “Element” if you think there's a chance they would ever
>> arise as associated types of the same type but with distinct identity.
>> 
>> Another possibility, if you think that might be about to happen, is that
>> you're using conformance when you should use aggregation.  For example,
>> an Int has everything it needs to be a Sequence and/or Iterator (n to
>> infinity), a Collection (of numbers from zero to its bitWidth), etc.,
>> but *should* it conform to those protocols?  IMO probably not.  If you
>> find yourself hard pressed to describe what something *is* in a few
>> words, it may be conforming to too many protocols.
>
> Additionally, I find that when a type is representable in multiple
> overlapping ways (where “overlapping” is meant quite broadly), it can
> be good to create wrappers for those conformances.

Jah, that's what I meant to imply, but failed to spell out.  Thanks for
clarifying, Karl!

>
>
> For example, you might try:
>
> Struct MyThing {
> }
>
> extension MyThing {
>
> var foo: Foo { return MyThing.FooWrapper(self) }
> var bar: Bar { return MyThing.BarWrapper(self)  }
>
> struct FooWrapper: Foo {
> let base: MyThing
> init(_ wrapping: MyThing) { self.base = wrapping }
>
> // Implement ‘Foo’ using data from ‘base’.
> }
> }
>
> let something = MyThing()
>
> takesAFoo(something.foo)
> takesABar(something.bar)
>
> This is analogous to how String is represented — the data is stored once, and 
> there are multiple
> Collection conformances which interpret the data in different ways (as 
> graphemes, or as a collection
> of non-character-boundary code-units in various encodings).

-- 
-Dave
___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] Associatedtype Naming Conventions

2017-06-06 Thread Dave Abrahams via swift-users

on Wed May 31 2017, Steven Brunwasser  wrote:

> Yes, I understand this. I was just wondering if there was a naming
> convention I should use to differentiate them.

I would try to find something more specific and descriptive than
“Container” and “Element” if you think there's a chance they would ever
arise as associated types of the same type but with distinct identity.

Another possibility, if you think that might be about to happen, is that
you're using conformance when you should use aggregation.  For example,
an Int has everything it needs to be a Sequence and/or Iterator (n to
infinity), a Collection (of numbers from zero to its bitWidth), etc.,
but *should* it conform to those protocols?  IMO probably not.  If you
find yourself hard pressed to describe what something *is* in a few
words, it may be conforming to too many protocols.

> Should I use a few letters as a prefix? Should I use the full protocol name
> as a prefix? Or is there another suggestion for a naming convention?
>
> I'm also curious about any naming conventions I should use to get around
> collisions with other libraries' protocol associatedtypes.
>
> On May 31, 2017 at 16:26:52, Slava Pestov (spes...@apple.com) wrote:
>
>>
>> On May 31, 2017, at 4:16 PM, Steven Brunwasser 
>> wrote:
>>
>> Basically, my library contains a bunch of collection-like protocols, which
>> can be combined in different ways and can be compatible with each other in
>> certain combinations when the proper types align. Naturally, they all have
>> an Element associatedtype, but I need to allow for the possibility where
>> two of these collection protocols are implemented in the same structure
>> that requires different type definitions for each protocols' Element.
>>
>>
>> Oh, I understand now. This is intentionally not supported — associated
>> types with the same name from different protocols must all be implemented
>> by the same typealias in the conforming type.
>>
>> Slava
>>
>>
>> I’ve been trying to make some other protocols to simplify some
>> definitions, but specifying a parent protocol’s associated type within a
>> child protocol doesn’t seem to work.
>>
>> protocol Buzz: Bar {
>> typealias Container = A
>> }
>>
>> struct BuzzImpl: Buzz {} // *error: type ‘BuzzImpl' does not conform to
>> protocol ‘Buzz'*
>>
>> On May 31, 2017 at 4:02:43 PM, Slava Pestov (spes...@apple.com) wrote:
>>
>> Can you give an example of a problematic name collision? Does fully
>> qualifying names not help?
>>
>> Slava
>>
>> On May 31, 2017, at 4:01 PM, Steven Brunwasser via swift-users <
>> swift-users@swift.org> wrote:
>>
>> Hi,
>>
>> I have a library which uses a few generic protocols with identically named
>> associated types that may not always be specified identically by
>> implementors.
>>
>> protocol Foo {
>> associatedtype Container
>> associatedtype Element
>> }
>>
>> protocol Bar {
>> associatedtype Container
>> associatedtype Element
>> }
>>
>> struct Baz: Foo, Bar {
>> // Implement using two different Container/Element types.
>> }
>>
>> Is there a consensus on some naming convention for associatedtypes to
>> mitigate name collisions?
>> Would it be acceptable to add namespace prefixes to these types?
>>
>> protocol Foo {
>> associatedtype FooContainer
>> associatedtype FooElement
>> }
>>
>> I’m using the dictionary and thesaurus to find some alternative names I
>> could use, but the ones already used are so the most sensical semantically.
>>
>> Do you have any suggestions?
>>
>> Thanks,
>> - Steve Brunwasser
>> ___
>> swift-users mailing list
>> swift-users@swift.org
>> https://lists.swift.org/mailman/listinfo/swift-users
>>
>>
>>
> ___
> swift-users mailing list
> swift-users@swift.org
> https://lists.swift.org/mailman/listinfo/swift-users
>

-- 
-Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] Help! Slicing an array is very expensive

2017-05-17 Thread Dave Abrahams via swift-users

on Wed May 10 2017, Rick Mann  wrote:

>> On May 10, 2017, at 11:52 , Joe Groff  wrote:
>> 
>> 
>>> On May 8, 2017, at 4:47 PM, Rick Mann via swift-users 
>>>  wrote:
>>> 
>
>>> I have this C library that interacts with some hardware over the
>>> network that produces a ton of data. It tells me up front the
>>> maximum size the data might be so I can allocate a buffer for it,
>>> then does a bunch of network requests downloading that data into
>>> the buffer, then tells me when it's done and what the final,
>>> smaller size is.
>>> 
>>> Thanks to previous discussions on the list, I settled on using a
>>> [UInt8] as the buffer, because it let me avoid various
>>> .withUnsafePointer{} calls (I need the unsafe buffer pointer to
>>> live outside the scope of the closures). Unfortunately, When I go
>>> to shrink the buffer to its final size with:
>>> 
>>>   self.dataBuffer = Array(self.dataBuffer![0 ..< finalBufferSize])
>>> 
>>> This ends up taking over 2 minutes to complete (on an iPad Pro). 
>>> finalBufferSize is very large,
> 240 MB, but I think it's doing a very naive copy.
>>> 
>>> I've since worked around this problem, but is there any way to improve on 
>>> this?
>> 
>> `self.dataBuffer!.removeSubrange(finalBufferSize ..<
>> self.dataBuffer!.endIndex)` might be more efficient. However,
>> copying an array of bytes definitely shouldn't be that slow, so is
>> worth a bug report.
>> 
>> -Joe
>
> Here you go: https://bugs.swift.org/browse/SR-4856

Did you compile this with -Onone or -O?

-- 
-Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] Help! Slicing an array is very expensive

2017-05-17 Thread Dave Abrahams via swift-users

on Mon May 08 2017, Rick Mann  wrote:

> I have this C library that interacts with some hardware over the
> network that produces a ton of data. It tells me up front the maximum
> size the data might be so I can allocate a buffer for it, then does a
> bunch of network requests downloading that data into the buffer, then
> tells me when it's done and what the final, smaller size is.
>
> Thanks to previous discussions on the list, I settled on using a
> [UInt8] as the buffer, because it let me avoid various
> .withUnsafePointer{} calls (I need the unsafe buffer pointer to live
> outside the scope of the closures). Unfortunately, When I go to shrink
> the buffer to its final size with:
>
> self.dataBuffer = Array(self.dataBuffer![0 ..< finalBufferSize])
>
> This ends up taking over 2 minutes to complete (on an iPad Pro). 
> finalBufferSize is very large, 240
> MB, but I think it's doing a very naive copy.

This shouldn't be expensive.  Please file an issue with a reproducer at
http://bugs.swift.org and we'll look into it.

> I've since worked around this problem, but is there any way to improve on 
> this?
>
> Thanks,

-- 
-Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] Is this really a race condition?

2017-03-01 Thread Dave Abrahams via swift-users

on Wed Mar 01 2017, Edward Connell  wrote:

> The thread sanitizer on Linux is reporting that I have race conditions in
> libswiftcore. 

The only one we currently know about that's actually in libswiftcore is
the one addressed by https://github.com/apple/swift/pull/7183

> I eliminated enough code down to this trivial example. Is there really
> a race condition here or are these bogus errors?
>
> let count = 1000
> var items = [[UInt8]?](repeating: nil, count: count)
>
> DispatchQueue.concurrentPerform(iterations: count) {
> items[$0] = [UInt8](repeating: 7, count: 10)
> }
>
> My real scenario is retrieving data asynchronously, so I just threw in a
> buffer assignment.


>
> Thanks, Ed
>
> ==
> WARNING: ThreadSanitizer: data race (pid=30720)
>   Read of size 8 at 0x7d908028 by thread T16:
> #0 memcpy  (libtsan.so.0+0x0002617a)
> #1 _TwCcOs31_ClosedRangeIndexRepresentation 
> (libswiftCore.so+0x0027e0fa)
>
>   Previous write of size 8 at 0x7d908028 by main thread:
> #0 memcpy  (libtsan.so.0+0x0002617a)
> #1 _TwCcOs31_ClosedRangeIndexRepresentation 
> (libswiftCore.so+0x0027e0fa)
>
>   Location is heap block of size 8032 at 0x7d908000 allocated by main
> thread:
> #0 malloc  (libtsan.so.0+0x000254a3)
> #1 swift_slowAlloc  (libswiftCore.so+0x002ee3e5)
>
>   Thread T16 (tid=30917, running) created by main thread at:
> #0 pthread_create  (libtsan.so.0+0x00027577)
> #1 manager_workqueue_additem
> /home/buildnode/disk2/workspace/oss-swift-3.0-package-linux-ubuntu-16_04/swift-corelibs-libdispatch/libpwq/src/posix/manager.c:815
> (libdispatch.so+0x0007c6b1)
>
> SUMMARY: ThreadSanitizer: data race ??:0 memcpy
> ==
> ==
> WARNING: ThreadSanitizer: data race (pid=30720)
>   Write of size 8 at 0x7d0c00015d80 by thread T16:
> #0 free  (libtsan.so.0+0x00025819)
> #1 _TwXxOs31_ClosedRangeIndexRepresentation 
> (libswiftCore.so+0x0027e071)
>
>   Previous write of size 8 at 0x7d0c00015d80 by main thread:
> #0 malloc  (libtsan.so.0+0x000254a3)
> #1 swift_slowAlloc  (libswiftCore.so+0x002ee3e5)
>
>   Thread T16 (tid=30917, running) created by main thread at:
> #0 pthread_create  (libtsan.so.0+0x00027577)
> #1 manager_workqueue_additem
> /home/buildnode/disk2/workspace/oss-swift-3.0-package-linux-ubuntu-16_04/swift-corelibs-libdispatch/libpwq/src/posix/manager.c:815
> (libdispatch.so+0x0007c6b1)
>
> SUMMARY: ThreadSanitizer: data race ??:0 __interceptor_free
> ==
> ==
> WARNING: ThreadSanitizer: data race (pid=30720)
>   Write of size 8 at 0x7d90a028 by thread T20:
> #0 free  (libtsan.so.0+0x00025819)
> #1 _TZFSa11_copyBufferfRGVs22_ContiguousArrayBufferx_T_ 
> (libswiftCore.so+0x0010884e)
>
>   Previous read of size 8 at 0x7d90a028 by thread T17:
> #0 memcpy  (libtsan.so.0+0x0002617a)
> #1 _TwCcOs31_ClosedRangeIndexRepresentation 
> (libswiftCore.so+0x0027e0fa)
>
>   Thread T20 (tid=30921, running) created by main thread at:
> #0 pthread_create  (libtsan.so.0+0x00027577)
> #1 manager_workqueue_additem
> /home/buildnode/disk2/workspace/oss-swift-3.0-package-linux-ubuntu-16_04/swift-corelibs-libdispatch/libpwq/src/posix/manager.c:815
> (libdispatch.so+0x0007c6b1)
>
>   Thread T17 (tid=30918, running) created by main thread at:
> #0 pthread_create  (libtsan.so.0+0x00027577)
> #1 manager_workqueue_additem
> /home/buildnode/disk2/workspace/oss-swift-3.0-package-linux-ubuntu-16_04/swift-corelibs-libdispatch/libpwq/src/posix/manager.c:815
> (libdispatch.so+0x0007c6b1)
>
> SUMMARY: ThreadSanitizer: data race ??:0 __interceptor_free
> ==
> ==
> WARNING: ThreadSanitizer: data race (pid=30720)
>   Read of size 8 at 0x7d906028 by thread T23:
> #0 memcpy  (libtsan.so.0+0x0002617a)
> #1 _TwCcOs31_ClosedRangeIndexRepresentation 
> (libswiftCore.so+0x0027e0fa)
>
>   Previous write of size 8 at 0x7d906028 by main thread:
> #0 malloc  (libtsan.so.0+0x000254a3)
> #1 swift_slowAlloc  (libswiftCore.so+0x002ee3e5)
>
>   Location is heap block of size 8032 at 0x7d906000 allocated by main
> thread:
> #0 malloc  (libtsan.so.0+0x000254a3)
> #1 swift_slowAlloc  (libswiftCore.so+0x002ee3e5)
>
>   Thread T23 (tid=30924, running) created by main thread at:
> #0 pthread_create  (libtsan.so.0+0x00027577)
> #1 manager_workqueue_additem
> /home/buildnode/disk2/workspace/oss-swift-3.0-package-linux-ubuntu-16_04/swift-corelibs-libdispatch/libpwq/src/posix/manager.c:815
> (libdispatch.so+0x0007c6b1)
>
> SUMMARY: ThreadSanitizer: data race ??:0 memcpy
> ==
> ==
> WARNING: ThreadSanitizer: data race (pid=30720)
>   Write of size 8 at 0x7d92e000 by thread T19:
> #0 free  (libtsan.so.0+0x00025819)
> #1 

Re: [swift-users] Collection Oddities

2017-02-09 Thread Dave Abrahams via swift-users

on Tue Feb 07 2017, Guillaume Lessard  wrote:

>> On 7 févr. 2017, at 21:57, Slava Pestov  wrote:
>> 
>>> 
>>> On Feb 7, 2017, at 8:14 PM, Guillaume Lessard via swift-users 
>>>  wrote:
>>> 
>
>>> I keep running into weird things with Swift 3 Collections.
>>> 
>>> A) Collection has its count property defined as an Int via IndexDistance:
>>> 
>>> public protocol Collection : Indexable, Sequence {
>>>   associatedtype IndexDistance : SignedInteger = Int  // line 182 in 
>>> Collection.swift
>>>   public var count: IndexDistance { get } // line 776
>>> }
>> 
>> This declaration specifies that the *default* associated type is
>> Int, not that it’s *always* Int. A Collection implementation is free
>> to use a different type as its IndexDistance if it wants.
>
> I see how I’d misunderstood that line.
>
> This being said, does this particular freedom really bring anything to
> the table? It is simply a counter (“the number of steps between a pair
> of indices”). On one hand, a “collection" that has in excess of
> Int.max/2 elements likely needs a different protocol; on the other,
> using a shorter type for a counter seems retro.

There are still plenty of 32-bit platforms that address 64-bit files,
which should be able to be modeled as Collections.

-- 
-Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] unsafeBitCast to Unimplemented Class

2017-02-07 Thread Dave Abrahams via swift-users

on Mon Feb 06 2017, Andrew Trick  wrote:

>> On Feb 6, 2017, at 8:51 PM, Dave Abrahams  wrote:
>> 
>> 
>> on Mon Feb 06 2017, Andrew Trick  wrote:
>> 
>
>>> Is a missing declaration a use case that needs to be supported?
>> 
>> I couldn't say.
>> 
>>> Wouldn’t it be more proper to use selector based dispatch in those
>>> cases?
>> 
>> Example, please?  I don't know what that means, though I probably should.
>> 
>> -- 
>> -Dave
>
> I phrased that as a question because I'm the last person who should be
> giving advice here... What I had in mind is this:
>
> if ([self isKindOfClass:NSClassFromString(@“Bar”)]) {
>   self.perform(@selector(FakeBarProtocol.foo))
> }
>
> It's not type safe, but it's a lot better than outright lying about
> the reference's dynamic type.

Presumably there's a way to express that in Swift, but if it uses
varargs I expect it's pretty darned inefficient.

-- 
-Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] unsafeBitCast to Unimplemented Class

2017-02-06 Thread Dave Abrahams via swift-users

on Mon Feb 06 2017, Andrew Trick  wrote:

> Is a missing declaration a use case that needs to be supported?

I couldn't say.

> Wouldn’t it be more proper to use selector based dispatch in those
> cases?

Example, please?  I don't know what that means, though I probably should.

-- 
-Dave
___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] unsafeBitCast to Unimplemented Class

2017-02-04 Thread Dave Abrahams via swift-users

on Fri Feb 03 2017, Saagar Jha  wrote:

> Hello,
>
> I’m having an issue migrating some old Objective-C code that looks like this:
>
> @implementation Foo
>
> - (void)load {
>   // Swizzle one of Bar’s methods to call Foo’s baz method
> }
>
> - (void)baz {
>   [self baz];
>   if ([self isKindOfClass:NSClassFromString(@“Bar”)]) {
>   Bar *bar = (Bar *)self; // I can’t migrate this
>   // work with bar
>   }
> }
>
> @end
>
> I’m trying to cast self to a Bar at runtime, and use it to call Bar’s 
> methods. Sounds like an easy
> to task for unsafeBitCast, right? The issue is that I don’t have access to 
> the implementation of
> Bar’s class at compile time (this is a plugin, so it’s loaded by another 
> application which contains
> Bar). In Objective-C I can create a header and stick a dummy interface for 
> Bar in it; the cast will
> work if Bar exists at runtime. However, in Swift, unsafeBitCast requires me 
> to use Bar.self, which
> does not exist. Is there any way to get this cast to work?

Bar.self exists if you have a declaration of it exposed to swift, which
would be required for all the “work with bar” code above.  If you don't
have Bar.self, it's because there's no declaration visible to your Swift
code.  My usual workaround would be to declare an @objc protocol having
the bar APIs you want to use, and then cast self to an instance of that
@objc protocol.  The right way to do that is by using
UnsafePointer.withMemoryRebound(to: ), e.g.

  var mutableSelf = self // can't get pointer to immutable value
  withUnsafePointer(to: ) { selfPtr in
selfPtr.withMemoryRebound(to: BarProtocol, capacity: 1) { barPtr in
  let bar = barPtr.pointee
  // work with bar
}
  }

HTH,

-- 
-Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] Implementing signum

2016-11-28 Thread Dave Abrahams via swift-users

on Sun Nov 20 2016, Hooman Mehr  wrote:

> Let me explain this a bit further:
>
> Swift generic programming is very different from C++ template programming. 
> Swift compiler needs to
> type-check generic code on spot, not while instantiating the template 
> (because in Swift,
> instantiation can occur at runtime if the generic code is from a different 
> module).
>
> This means that it should know what operations will be supported on the type 
> being extended. Your
> `Signumable` defines only a single function. IF you extend `Signumable` to 
> provide an
> implementation, you can’t refer to any function other than `sgn()`, but you 
> need more to be able to
> implement sin(). This is don though generic constraints. You need to 
> constrain the type to which
> your extension applies. The minimal contains that you need are: 
> `ExpressibleByIntegerLiteral` and
> `Comparable` so that you can write the algorithm as follow:
>
> The way you wrote it, would require more defined operations (subtraction):
>
> protocol Signumable
> {
> func sgn() -> Self
> }
>
> extension Signumable where Self: ExpressibleByIntegerLiteral & Comparable
> {
> func
> sgn()
> -> Self
> {
> if 0 < self { return 1 }
> if self < 0 { return -1 }
> return 0
> }
> }
>
> This can potentially work on any integer (including unsigned) and floating 
> point type and any other
> type that happens to support those two protocols. But it does not work yet, 
> because those types do
> not automatically conform to `Signumable`. To make them conform you need a 
> bit of boilerplate:
>
> extension Int: Signumable {}
> extension Int8: Signumable {}
> extension Int16: Signumable {}
> extension Int32: Signumable {}
> extension Int64: Signumable {}
> extension UInt: Signumable {}
> extension UInt8: Signumable {}
> extension UInt16: Signumable {}
> extension UInt32: Signumable {}
> extension UInt64: Signumable {}
> extension Float32: Signumable {}
> extension Float64: Signumable {}
> extension Float80: Signumable {}
>
> The problem is, if a new numeric type is defined say a rational number type
> , it won’t 
> conform automatically
> and you will have to declare its conformance as above. For this reason, it is 
> better to try to find
> an existing standard protocol to extend instead of introducing your own 
> protocol for such things.
>
> So, as others suggested, it is better to extend the existing `SignedNumber` 
> protocol instead of
> introducing your own `Signumable`, unless if you need to write other generic 
> algorithms that need
> your protocol as their constraints.

The deeper generic programming principle here has to do with how
requirements are clustered into protocols and whether that limits what
you can express.  Are there any Signumables that can't also efficiently
implement the requirements of SignedNumber (and vice-versa)?  If not,
these two things are fundamentally, in some sense, the same protocol and
should be merged.  If so, there may be a reason to have a distinct
protocol, so that you can write algorithms constrained to that protocol
that give protocols that depend on the operation.

-- 
-Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] Int32.divideWithOverflow

2016-11-09 Thread Dave Abrahams via swift-users

on Wed Nov 09 2016, Peter W A Wood  wrote:

> I am using Swift to generate some tests with overflowing 32-bit
> integers. I have used the Int32.WithOverflow functions but have
> come across a problem dividing Int32.min by -1 with overflow. I get an
> overflow error:
>
> error: division '-2147483648 / -1' results in an overflow
> Int32.divideWithOverflow(Int32.min, -1)
>
> Is this the expected behaviour?

Yes.

   -Int64(Int32.min) > Int64(Int32.max)

which is to say that the result of the division can't be expressed as
an Int32.

-- 
-Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] The value of enums

2016-11-06 Thread Dave Abrahams via swift-users

on Sun Nov 06 2016, Nevin Brackett-Rozinsky 
 wrote:

> …oh, I just realized we’re on -users not -evolution here. Perhaps I’ll
> bring this up next time switch expressions are proposed.

Thanks ;-)

-- 
-Dave
___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] The value of enums

2016-11-06 Thread Dave Abrahams via swift-users

on Sun Nov 06 2016, Tino Heth  wrote:

> Enums are a fundamental part of Swift, so I guess they won't change
> much — but I wonder if anyone shares my observations in real-life use…
>
> Afair, there are three different types of enums:
> - Enums with raw values
> - enums with associated objects
> - Plain enums (no underlying value)
>
> I use the first type quite often (as a convenient way to create string
> constants, or for serialization), but see no real value in plain enums
> (they offer nothing over enums backed with a raw value).
>
> The second type is special:
> It looks like a really cool concept, and and I started several designs
> based on them — just to realize later that structs and classes are a
> better fit.
> My conclusion so far is that enums perform bad as soon as you want to
> attach additional data or behavior; one or two computed properties are
> ok, but those switch-statements quickly become a burden.
> There are some options to work around this problem, but I guess I'll
> just stay away from enums with associated objects by default (with the
> exception of error-types — imho those can be modeled quite nicely).
>
> So, that's my current perception, and I'm curious if others had
> similar experiences — or, even more interesting, completely different
> observations and elegant solutions based on enums.

I have personally always found that exuberant use of that kind of enum
results in ergonomics and readability difficulties.  There are several
things we have thought of that could potentially improve the situation,
most notably exposing each case as an optional property.  I'd also
really like to see switch-expressions (as opposed to statements).  I'm
not sure if that's really all we need in order to allow enums to reach
their potential, though.

-- 
-Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] What is "binding" memory?

2016-11-03 Thread Dave Abrahams via swift-users

on Wed Nov 02 2016, Andrew Trick  wrote:

>> On Nov 2, 2016, at 3:50 PM, Dave Abrahams  wrote:
>> 
>>> The original poster seemed to have the impression that the operation
>>> of binding memory itself might affect program state, 
>> 
>> Formally speaking, it does!
>
> Oh boy. I keep failing at this. How does one formally distinguish
> between semantic state and actual state?

That's the point; you don't. :-)

-- 
-Dave
___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] What is "binding" memory?

2016-11-02 Thread Dave Abrahams via swift-users

on Wed Nov 02 2016, Andrew Trick  wrote:

>> On Nov 2, 2016, at 12:58 PM, Dave Abrahams via swift-users 
>> <swift-users@swift.org> wrote:
>> 
>>> At the top of the migration guide is a link to the memory model explanation:
>>>
> https://github.com/apple/swift-evolution/blob/master/proposals/0107-unsaferawpointer.md#memory-model-explanation
>>> 
>
>>> "A memory location's bound type is an abstract, dynamic property of the 
>>> memory used to formalize
>>> type safety.”
>>> 
>>> I’m not sure I like the “prepares the memory” language myself. Binding
>>> memory communicates to the compiler that the memory locations are safe
>>> for typed access. Nothing happens at runtime--until someone writes a
>>> type safety sanitizer. 
>> 
>> Well, that's a slight overstatement IMO.  Sanitizers aside, the main
>> reason for these binding operations is that if you leave them out,
>> something different *will* happen at runtime... something that will make
>> your code do the wrong thing.
>> 
>> What I would say is that binding the memory has no immediate runtime
>> cost... but it's absolutely required if you want your program to behave
>> (and sometimes behaving correctly is a little slower than misbehaving).
>
> Good clarification. I really did not mean to imply that binding memory
> to a type has no effect on runtime behavior. Taken out of context,
> “nothing happens at runtime” is quite an understatement.
>
> The original poster seemed to have the impression that the operation
> of binding memory itself might affect program state, 

Formally speaking, it does!

> independent of any compiler optimization. I want to make it clear that
> a call to bindMemory(to:capacity:) has no observable runtime side
> effects at the point of the call. 

Only because you can't observe what memory is bound to.

> But I need to throw in an exemption for future sanitizers.

I don't think you do; sanitizer actions are allowed under undefined
behavior.

-- 
-Dave
___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] Localization in Swift.

2016-11-02 Thread Dave Abrahams via swift-users

on Wed Nov 02 2016, Jens Alfke  wrote:

>> On Nov 2, 2016, at 12:50 PM, Dave Abrahams via swift-users 
>> <swift-users@swift.org> wrote:
>> 
>> In my opinion, we can and must do much better for Swift.  If there's
>> something about “%” formatting that you particularly value, I'd like to
>> know about it, so I can make sure it's accomodated.
>
> It offers more control over formatting, like min/max widths, number
> base, decimal places, etc. Yes, you can do this in the code inside the
> interpolated string, but IMHO it’s awkward because it requires knowing
> a bunch of extra methods for string conversion, truncation, etc. It’s
> a lot easier for me to remember and type “%x” than it is to remember
> and type the method that converts an int to a hex string.

In my view this should look like 

  "... \(x.format(radix: 16, width: 12))... "

Where the possible arguments to format() are statically known to the
compiler (and code completion!) based on the type of x.

>
> Also (and more importantly for localization) the formatting details
> are part of the localizable format string, not hardwired. One example
> of this is formatting currency, where a US localization would use
> “$%.2f” but other currencies might call for more or fewer decimal
> places. 

Yep, I'm paying attention to that, thanks.

> There are other examples where one might swap format strings for other
> purposes like different-width layouts for monospaced/terminal output.

I think we can leverage the same mechanisms used for localization to
handle those.

> There’s also a nonstandard extension used by Cocoa/CF’s formatters,
> that allows the parameters to be reordered. (I haven’t used it so I
> don’t know the syntax offhand.) This is of course important for
> localization, to follow a language’s grammar.

Right, that's crucial.

> I think these features could be added to interpolation. Just as a
> quick idea, maybe a syntax that allows formatting metacharacters to be
> added at the start of the interpolation, like “Please pay $\((.2)
> total)” where the “(.2) specifies two decimal places, or “The address
> is \((x) addr)”.

I think the “.format(...)” approach is better, but it's equally
important that there are sufficient outside-the-Swift-source knobs for
localizers to add language-specific formatting parameters.

-- 
-Dave
___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] What is "binding" memory?

2016-11-02 Thread Dave Abrahams via swift-users

on Tue Nov 01 2016, Andrew Trick  wrote:

>> On Nov 1, 2016, at 11:55 AM, Manfred Schubert via swift-users 
>>  wrote:
>> 
>> The "UnsafeRawPointer Migration" guide talks about "binding memory
>> to a type“ as if that was a well known term. I have never heard of
>> it yet though, and googling it returns no relevant results. I do not
>
>> understand what binding memory is supposed to do.
>> 
>> The migration guide says "Binding uninitialized memory to a type
>> prepares the memory to store values of that type“, but clearly raw
>> memory does not need to be prepared (and cannot be) to hold any
>> arbitrary type and value.
>> 
>> So what is this for, what does it actually do, and to whom is it done (the 
>> raw pointer, or the
> typed pointer which is returned, or the raw memory)?
>> 
>> 
>> Manfred
>
> Hi Manfred,
>
> At the top of the migration guide is a link to the memory model explanation:
> https://github.com/apple/swift-evolution/blob/master/proposals/0107-unsaferawpointer.md#memory-model-explanation
>
> "A memory location's bound type is an abstract, dynamic property of the 
> memory used to formalize
> type safety.”
>
> I’m not sure I like the “prepares the memory” language myself. Binding
> memory communicates to the compiler that the memory locations are safe
> for typed access. Nothing happens at runtime--until someone writes a
> type safety sanitizer. 

Well, that's a slight overstatement IMO.  Sanitizers aside, the main
reason for these binding operations is that if you leave them out,
something different *will* happen at runtime... something that will make
your code do the wrong thing.

What I would say is that binding the memory has no immediate runtime
cost... but it's absolutely required if you want your program to behave
(and sometimes behaving correctly is a little slower than misbehaving).

> It affects the abstract state of the memory location, independent of
> the pointer variable used to access that memory. Binding memory
> returns a typed pointer for convenience and clarity, but there’s
> nothing special about that particular pointer value.
>
> Initialized memory is always bound to some type. A rawpointer can be
> used to access that memory without knowing its bound type.
>
> -Andy
> ___
> swift-users mailing list
> swift-users@swift.org
> https://lists.swift.org/mailman/listinfo/swift-users

-- 
-Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] Localization in Swift.

2016-11-02 Thread Dave Abrahams via swift-users

on Tue Nov 01 2016, Jens Alfke  wrote:

>> On Nov 1, 2016, at 10:40 PM, Zhao Xin  wrote:
>> 
>> For example, if I want show the user that I have to ask him to give me 
>> permission of a folder, the
> `url.path` has no need to translate.
>
> We’re getting off-topic, but paths do need to be translated, at least
> on Mac systems. The names of many standard folders like “Applications”
> and “Documents” are hardwired to English in the filesystem but are
> localized in the UI. Some application names get localized too (there’s
> a table in the app’s Info.plist that can substitute localized names.)
>
> Anyway, string interpolation is convenient, but I wouldn’t say it
> should be the only way to format strings in Swift; it’s a lot less
> flexible than the C-style “%” substitutions. For comparison, even
> though C++’s iostreams use “<<“ to format strings by concatenation, I
> still end up using “%” based formatting a lot, depending on the use
> case.

I'm actually working on design in this area right now.

%-style formatting has the following drawbacks

- for anyone who doesn't use them regularly they are cryptic and
  complex, as the printf (3) man page attests.

- the spelling of these placeholders must match up to the types of the
  arguments, in the right order, or the behavior is undefined.  Some
  limited support for compile-time checking of this correspondence could
  be implemented, but only for the cases where the format string is a
  literal.

- there's no reasonable way to extend the formatting vocabulary to cover
  the needs of new types: you are stuck with what's in the box.

In my opinion, we can and must do much better for Swift.  If there's
something about “%” formatting that you particularly value, I'd like to
know about it, so I can make sure it's accomodated.

Thanks,

-- 
-Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] dispatch concurrent map: is this right?

2016-10-31 Thread Dave Abrahams via swift-users

on Mon Oct 31 2016, Karl  wrote:

>> On 31 Oct 2016, at 05:15, Dave Abrahams <dabrah...@apple.com> wrote:
>> 
>> 
>> on Sun Oct 30 2016, Karl > <http://razielim-at-gmail.com/>> wrote:
>> 
>
>>>> On 30 Oct 2016, at 19:23, Dave Abrahams via swift-users 
>>>> <swift-users@swift.org> wrote:
>>>> 
>>>> 
>>>> on Sun Oct 30 2016, Karl  wrote:
>>>> 
>>> 
>>>>>> On 30 Oct 2016, at 09:15, Karl <raziel.im+swift-us...@gmail.com> wrote:
>>>>>> 
>>>>>> I had the need for a concurrent map recently. I had a part of a
>>>>>> program which needed to read chunks of data and concurrently process
>>>>>> them and assemble the results in an array. This isn’t necessarily as
>>>>>> obvious as it sounds, because of arrays being value types. I came up
>>>>>> with the following snippet which I’d like to check for correctness;
>>>>>> it could also be helpful to others.
>>>>>> 
>>>>>> Perhaps this is something Dispatch should provide out-of-the-box?
>>>>>> 
>>>>>> - Karl
>>>>> 
>>>>> Ah one second, I was refactoring this and forgot to test it. Here’s the 
>>>>> actual code:
>>>> 
>>>> A map presumably requires an input 
>>> 
>>> DispatchQueue.concurrentMap maps a Range -> T, but since the
>>> range is always 0..<n, we only ask for the value of n. It could also
>>> be written quite naturally as an extension on Range and build
>>> everything on top of it.
>> 
>> Sorry, I wrote “a map presumably requires an input” before I realized
>> what you were doing.  I should have deleted that.
>> 
>>>> 
>>>>> extension DispatchQueue {
>>>>> 
>>>>> static func concurrentMap(iterations: Int, execute block: (Int) -> T) 
>>>>> -> [T] {
>>>>> 
>>>>>   let __result = UnsafeMutableRawBufferPointer.allocate(count: iterations 
>>>>> * MemoryLayout.stride)
>>>>>   defer { __result.deallocate() }
>>>>>   let _result  = __result.baseAddress?.assumingMemoryBound(to: T.self)
>>>> 
>>>> You never bound the memory to T, so this will be undefined behavior.  
>>>> 
>>>>>   let result   = UnsafeMutableBufferPointer(start: _result, count: 
>>>>> iterations)
>>>>>   concurrentPerform(iterations: iterations) { idx in
>>>>> result[idx] = block(idx)
>>>> 
>>>> You also never initialized the Ts in that memory region, so assigning
>>>> into them will also be undefined behavior.
>>>> 
>>>>>   }
>>>>>   return Array(result)
>>>>> }
>>>>> }
>>>>> 
>>>>> extension Array {
>>>>> func concurrentMap(execute block: (Element)->T) -> [T] {
>>>>>   return DispatchQueue.concurrentMap(iterations: count) { block(self[$0]) 
>>>>> }
>>>>> }
>>>>> }
>>>>> 
>>>>> Unfortunately I don’t think there’s a way to get an array to take over a 
>>>>> +1
>>>>> UnsafeMutableBufferPointer without copying.
>>>> 
>>>> The only correct way to do this without creating intermediate storage is
>>>> to have a way to initialize your result elements, e.g.:
>>>> 
>>>> import Dispatch
>>>> 
>>>> protocol DefaultInitializable {
>>>>   init()
>>>> }
>>>> 
>>>> extension RandomAccessCollection {
>>>>   func concurrentMap(_ transform: (Iterator.Element)->T) -> [T]
>>>>   where T : DefaultInitializable {
>>>> var result = Array(
>>>>   repeating: T(), count: numericCast(self.count))
>>>> 
>>>> DispatchQueue.concurrentPerform(iterations: result.count) {
>>>>   offset in 
>>>>   result[offset] = transform(
>>>> self[index(startIndex, offsetBy: numericCast(offset))])
>>>> }
>>>> return result
>>>>   }
>>>> }
>>>> 
>>>> extension Int : DefaultInitializable {  }
>>>> 
>>>> print((3..<20).concurrentMap { $0 * 2 })
>>>> 
>>> 
>>> I had a go at doing that before, using Optional and unwrapping at
>>&

Re: [swift-users] Element vs. Iterator.Element

2016-10-31 Thread Dave Abrahams via swift-users

on Mon Oct 31 2016, Toni Suter  wrote:

> Hi,
>
> This extension on Array works as expected:
>
> extension Array where Element: CustomStringConvertible {
> func f(_ x: Element) -> String {
> return x.description
> }
> }
>
> But when I use Iterator.Element instead, I get an error message (error: value 
> of type 'Element' has
> no member 'description'):
>
> extension Array where Iterator.Element: CustomStringConvertible {
> func f(_ x: Iterator.Element) -> String {
> return x.description
> }
> }
>
> I assume this is a type checker bug, but before I report it, I wanted to make 
> sure that that’s
> really the case. Or is there a difference between Element and
> Iterator.Element?

There shouldn't be.  It's a bug, IMO.

-- 
-Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] dispatch concurrent map: is this right?

2016-10-30 Thread Dave Abrahams via swift-users

on Sun Oct 30 2016, Dave Abrahams  wrote:

>> I quite like the API as an extension on Range. I think it would be a
>> nice addition to Dispatch (once we start allowing additive proposals):
>>
>> extension Range where Bound : Strideable, Bound.Stride : SignedInteger {
>>
>>   func concurrentMap(_ transform: (Bound) -> T) -> [T] {
>> let n= numericCast(count) as Int
>> let buffer = UnsafeMutablePointer.allocate(capacity: n)
>>
>> DispatchQueue.concurrentPerform(iterations: n) {
>>   (buffer + $0).initialize(to: transform(lowerBound + numericCast($0)))
>> }
>>
>> // Unfortunately, the buffer is copied when making it an Array.
>> defer { buffer.deallocate(capacity: n) }
>> return Array(UnsafeMutableBufferPointer(start: buffer, count: n))
>>   }
>> }
>>
>> extension Collection {
>>   func concurrentMap(_ transform: (Iterator.Element)->T) -> [T] {
>>
>> // ‘as Range’ because CountableRange is a collection, causing the 
>> function to be recursive.
>> return ((0..>   transform(self[index(startIndex, offsetBy: numericCast($0))])
>> }
>>   }
>> }
>
> I see the beauty in what you're doing here, but I don't see any
> advantage to it for users.  Now Range (which will be collapsed with
> CountableRange in Swift 4) will have two overloads of concurrentMap.  In
> general, avoidable overloads are bad for the user experience.

Oh, and I should add, a suite of parallel algorithms would be great, but
it should be implemented similarly to lazy, so instead of 

   x.concurrentMap { ... }.concurrentFilter { ... }

you'd write

   x.parallel.map { ... }.filter { ... }

Cheers,

-- 
-Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] dispatch concurrent map: is this right?

2016-10-30 Thread Dave Abrahams via swift-users

on Sun Oct 30 2016, Karl  wrote:

>> On 30 Oct 2016, at 19:23, Dave Abrahams via swift-users 
>> <swift-users@swift.org> wrote:
>> 
>> 
>> on Sun Oct 30 2016, Karl  wrote:
>> 
>
>>>> On 30 Oct 2016, at 09:15, Karl <raziel.im+swift-us...@gmail.com> wrote:
>>>> 
>>>> I had the need for a concurrent map recently. I had a part of a
>>>> program which needed to read chunks of data and concurrently process
>>>> them and assemble the results in an array. This isn’t necessarily as
>>>> obvious as it sounds, because of arrays being value types. I came up
>>>> with the following snippet which I’d like to check for correctness;
>>>> it could also be helpful to others.
>>>> 
>>>> Perhaps this is something Dispatch should provide out-of-the-box?
>>>> 
>>>> - Karl
>>> 
>>> Ah one second, I was refactoring this and forgot to test it. Here’s the 
>>> actual code:
>> 
>> A map presumably requires an input 
>
> DispatchQueue.concurrentMap maps a Range -> T, but since the
> range is always 0..<n, we only ask for the value of n. It could also
> be written quite naturally as an extension on Range and build
> everything on top of it.

Sorry, I wrote “a map presumably requires an input” before I realized
what you were doing.  I should have deleted that.

>> 
>>> extension DispatchQueue {
>>> 
>>>  static func concurrentMap(iterations: Int, execute block: (Int) -> T) 
>>> -> [T] {
>>> 
>>>let __result = UnsafeMutableRawBufferPointer.allocate(count: iterations 
>>> * MemoryLayout.stride)
>>>defer { __result.deallocate() }
>>>let _result  = __result.baseAddress?.assumingMemoryBound(to: T.self)
>> 
>> You never bound the memory to T, so this will be undefined behavior.  
>> 
>>>let result   = UnsafeMutableBufferPointer(start: _result, count: 
>>> iterations)
>>>concurrentPerform(iterations: iterations) { idx in
>>>  result[idx] = block(idx)
>> 
>> You also never initialized the Ts in that memory region, so assigning
>> into them will also be undefined behavior.
>> 
>>>}
>>>return Array(result)
>>>  }
>>> }
>>> 
>>> extension Array {
>>>  func concurrentMap(execute block: (Element)->T) -> [T] {
>>>return DispatchQueue.concurrentMap(iterations: count) { block(self[$0]) }
>>>  }
>>> }
>>> 
>>> Unfortunately I don’t think there’s a way to get an array to take over a +1
>>> UnsafeMutableBufferPointer without copying.
>> 
>> The only correct way to do this without creating intermediate storage is
>> to have a way to initialize your result elements, e.g.:
>> 
>>  import Dispatch
>> 
>>  protocol DefaultInitializable {
>>init()
>>  }
>> 
>>  extension RandomAccessCollection {
>>func concurrentMap(_ transform: (Iterator.Element)->T) -> [T]
>>where T : DefaultInitializable {
>>  var result = Array(
>>repeating: T(), count: numericCast(self.count))
>> 
>>  DispatchQueue.concurrentPerform(iterations: result.count) {
>>offset in 
>>result[offset] = transform(
>>  self[index(startIndex, offsetBy: numericCast(offset))])
>>  }
>>  return result
>>}
>>  }
>> 
>>  extension Int : DefaultInitializable {  }
>> 
>>  print((3..<20).concurrentMap { $0 * 2 })
>> 
>
> I had a go at doing that before, using Optional and unwrapping at
> the end — but it occurred to me that it would be very inefficient for
> things like Optional, and introduces more allocations.

Yeah, optional is not really a good choice for that application.

>> If you don't want the DefaultInitializable requirement (or some other
>> way to prepare initialized elements), you'll need to manage memory
>> yourself:
>> 
>>  extension RandomAccessCollection {
>>func concurrentMap(_ transform: (Iterator.Element)->T) -> [T] {
>>  let n = numericCast(self.count) as Int
>>  let p = UnsafeMutablePointer.allocate(capacity: n)
>>  defer { p.deallocate(capacity: n) }
>> 
>>  DispatchQueue.concurrentPerform(iterations: n) {
>>offset in
>>(p + offset).initialize(
>>  to: transform(
>>self[index(startIndex, offsetBy: numericCast(offset))]))
>>  }
>> 
>>  return Array(UnsafeMutableBufferPointer(

Re: [swift-users] dispatch concurrent map: is this right?

2016-10-30 Thread Dave Abrahams via swift-users

on Sun Oct 30 2016, Karl  wrote:

>> On 30 Oct 2016, at 09:15, Karl  wrote:
>> 
>> I had the need for a concurrent map recently. I had a part of a
>> program which needed to read chunks of data and concurrently process
>> them and assemble the results in an array. This isn’t necessarily as
>> obvious as it sounds, because of arrays being value types. I came up
>> with the following snippet which I’d like to check for correctness;
>> it could also be helpful to others.
>> 
>> Perhaps this is something Dispatch should provide out-of-the-box?
>> 
>> - Karl
>
> Ah one second, I was refactoring this and forgot to test it. Here’s the 
> actual code:

A map presumably requires an input 

> extension DispatchQueue {
>
>   static func concurrentMap(iterations: Int, execute block: (Int) -> T) -> 
> [T] {
>
> let __result = UnsafeMutableRawBufferPointer.allocate(count: iterations * 
> MemoryLayout.stride)
> defer { __result.deallocate() }
> let _result  = __result.baseAddress?.assumingMemoryBound(to: T.self)

You never bound the memory to T, so this will be undefined behavior.  

> let result   = UnsafeMutableBufferPointer(start: _result, count: 
> iterations)
> concurrentPerform(iterations: iterations) { idx in
>   result[idx] = block(idx)

You also never initialized the Ts in that memory region, so assigning
into them will also be undefined behavior.

> }
> return Array(result)
>   }
> }
>
> extension Array {
>   func concurrentMap(execute block: (Element)->T) -> [T] {
> return DispatchQueue.concurrentMap(iterations: count) { block(self[$0]) }
>   }
> }
>
> Unfortunately I don’t think there’s a way to get an array to take over a +1
> UnsafeMutableBufferPointer without copying.

The only correct way to do this without creating intermediate storage is
to have a way to initialize your result elements, e.g.:

  import Dispatch

  protocol DefaultInitializable {
init()
  }

  extension RandomAccessCollection {
func concurrentMap(_ transform: (Iterator.Element)->T) -> [T]
where T : DefaultInitializable {
  var result = Array(
repeating: T(), count: numericCast(self.count))

  DispatchQueue.concurrentPerform(iterations: result.count) {
offset in 
result[offset] = transform(
  self[index(startIndex, offsetBy: numericCast(offset))])
  }
  return result
}
  }

  extension Int : DefaultInitializable {  }

  print((3..<20).concurrentMap { $0 * 2 })

If you don't want the DefaultInitializable requirement (or some other
way to prepare initialized elements), you'll need to manage memory
yourself:

  extension RandomAccessCollection {
func concurrentMap(_ transform: (Iterator.Element)->T) -> [T] {
  let n = numericCast(self.count) as Int
  let p = UnsafeMutablePointer.allocate(capacity: n)
  defer { p.deallocate(capacity: n) }

  DispatchQueue.concurrentPerform(iterations: n) {
offset in
(p + offset).initialize(
  to: transform(
self[index(startIndex, offsetBy: numericCast(offset))]))
  }

  return Array(UnsafeMutableBufferPointer(start: p, count: n))
}
  }

This posting highlights a couple of weaknesses in the standard library
for which I'd appreciate bug reports:

1. No way to arbitrarily initialize an Array's storage.
2. UnsafeMutableBufferPointer doesn't have an allocating init

Thanks!

-- 
-Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] [Swift3][Linux][URLSession]: Core dump when trying to make simple HTTP request

2016-10-28 Thread Dave Abrahams via swift-users

Pasting a reply on behalf of Matt Wright (cc'd):

> On Oct 27, 2016, at 1:57 PM, Dave Abrahams  wrote:
> 
> 
> From: Steven Harms via swift-users 
> Subject: [Swift3][Linux][URLSession]: Core dump when trying to make simple 
> HTTP request
..
> Date: October 27, 2016 at 5:01:58 AM PDT
> To: swift-users@swift.org
> Reply-To: Steven Harms 
> 
> 
> Hello Swift,
> 
> I've been trying out Swift as a general utility language on the server 
> (replacing Ruby or Node). I'm trying to write a simple image retriever via 
> HTTP as a learning project.
> 
> Inspired by this [gist][], I've written the following:
> 
> let queue = DispatchQueue.global(qos: .background)
> 
> let sessionConfiguration = URLSessionConfiguration.default
> let session = URLSession(configuration: sessionConfiguration)
> 
> print("staring sync")
> queue.async(execute: {
> print(">>> [\(queue.label)]: At the queue start")
> print("x")
> let task = session.dataTask(with: URL(string: "http://google.com;)!, 
> completionHandler: {
> (data, response, error) in
> print("Task ran!")
> })
> print("y")
> task.resume()
> print("z")
> })
> print("ending sync")
> 
> With output:
> 
> staring sync
> ending sync
> 
> or...
> 
> staring sync
> ending sync
> >>> [com.apple.root.background-qos]: At the queue start
> x
> y
> y
> z
> 
> Whoa.
> 
> At this point I'm going to have to confess that I need some help clarifying 
> my model.
> 
> 1. How did point "y" get fired twice? Or how did it happen not at all?

The double-fire is something I can’t immediately come up with an
explanation. It might be specific to the Linux dispatch
implementation, which I’m not well versed on but it’s very strange
that it would print twice. Not firing at all is likely because his
snippet of code exited before the work was run on another thread. The
“main” thread here either has to wait for the session work to finish
explicitly, or call dispatch_main() to cede control of the main thread
to the system (and subsequently exit out of the tool somewhere else).

> 2. How did my callback for dataTask *never* fire? Even if the connection task 
> *failed* the handler
ought have fired, no?

Likely similar to (1), though if URLSession uses runloops (Linux?)
then it could also be because the runloop was never run anywhere. On
Darwin I’d suspect the runloop for URLSession wasn’t running, I don’t
know how it works on Linux.

> 3. I didn't want to bring this whole queue business into the
> picture, but it appears that without it the program exits before the
> handler has a chance to fire.

Probably similar to the issues in (1) and (2). If the snippet exits after 
running then a lot of this
asynchronously scheduled work will never happen.

> 4. Changing to a queue.sync from queue.async consistently produces the output 
> I expect, but does
not fire my completionHandler still.

This forces the queue.sync to run in-line (on the current thread) but
the snippet will then likely still exit before anything happens to
cause the URLSession to finish.

-- 
-Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] Why can I not filter or map a dictionary to another dictionary?

2016-10-28 Thread Dave Abrahams via swift-users

on Thu Oct 27 2016, Rick Mann  wrote:

>> On Oct 26, 2016, at 22:23 , Dave Abrahams via swift-users 
>> <swift-users@swift.org> wrote:
>> 
>> 
>> on Wed Oct 26 2016, Rick Mann  wrote:
>> 
>
>>> It seems fairly natural to want to do this:
>>> 
>>> let bigDictionary = ...
>>> let smallerDictionary = bigDictionary.filter { key, value in >> returning Bool> }
>> 
>>> Similarly, it seems natural to want to map this way.
>> 
>> It's reasonable for filter, but maybe not for map.  Map follows certain
>> laws, and one of them is that you get the same number of elements out as
>> you put in.  But you can easily map all keys to the same key, and the
>> law would be violated.
>
> Sure map would produce a dictionary of the same number of entries. I
> didn't mean to imply map would also filter. 

I think you're missing my point.  What result do you expect from

  {1:2, 3:4}.map { _ in (1, 1) }

? How many elements does it have?  Note that you can't have the same key
twice in a Dictionary.

> But I'm basically transforming a JSON dictionary into a new version of
> that dictionary with fewer elements. I'd like to first filter it, then
> map it, and have the result be a dictionary.

What we need are Dictionary initializers that operate on Sequences, per
https://github.com/apple/swift-evolution/blob/master/proposals/0100-add-sequence-based-init-and-merge-to-dictionary.md

Dictionary(merging: d.lazy.filter {... }.map {...})

That would get you the result you're looking for in a principled way,
without creating an intermediate Array.

-- 
-Dave
___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] Why can I not filter or map a dictionary to another dictionary?

2016-10-26 Thread Dave Abrahams via swift-users

on Wed Oct 26 2016, Rick Mann  wrote:

> It seems fairly natural to want to do this:
>
> let bigDictionary = ...
> let smallerDictionary = bigDictionary.filter { key, value in  returning Bool> }

> Similarly, it seems natural to want to map this way.

It's reasonable for filter, but maybe not for map.  Map follows certain
laws, and one of them is that you get the same number of elements out as
you put in.  But you can easily map all keys to the same key, and the
law would be violated.

-- 
-Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] Subsequences and shared indices

2016-10-16 Thread Dave Abrahams via swift-users

on Thu Oct 13 2016, Tim Vermeulen  wrote:

> Is it a requirement that collections share indices with its
> subsequence? 

Yes.

> Array and ArraySlice do share indices, which is why ArraySlice isn’t
> zero-based, and I think this is convenient. But String.CharacterView
> doesn’t seem to share indices with its subsequence (which is
> String.CharacterView as well). 

That's a bug.

> Consider this example:
>
> let foo = "foobar".characters
>
> let index = foo.index(foo.startIndex, offsetBy: 3)
> let bar = foo.suffix(from: index)   // "bar"
>
> foo[index]  // "b" :)
> foo[bar.startIndex] // "f" :(
>
> So does this mean that we can’t assume that collections and their
> subsequences share their indices (which could be very handy), or is
> this just a bug related to String.CharacterView?

The latter.

-- 
-Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] How to be DRY on ranges and closed ranges?

2016-10-16 Thread Dave Abrahams via swift-users

on Wed Oct 12 2016, Hooman Mehr  wrote:

>> On Oct 12, 2016, at 3:21 AM, Jean-Denis Muys via swift-users 
>>  wrote:
>> 
>> 
>> But this is not very DRY.
>> 
>> What would be a more idiomatic way?
>> 
>
> The more idiomatic way is to look at API design in a new way. Note these 
> points:
>
> 1. `Countable` variant is preferred when you want to deal with integer ranges 
> as it more closely
> matches the element type.
> 2. Both countable range variants share a common protocol conformance already:
> `RandomAccessCollection`
> 3. Swift API design prefers member functions to free functions.
>
> Hence a more idiomatic (Swifty) API would probably be something like this:
>
> extension RandomAccessCollection {
>
> func random() -> Iterator.Element? {
>
> guard count > 0 else { return nil }
>
> let offset = arc4random_uniform(numericCast(count))
>
> let i = index(startIndex, offsetBy: numericCast(offset))
>
> return self[i]
> }
> }
>
> Using the above, both cases work and there is no repetition:
>
> (4..<10).random()
> (4...9).random()
>
>
> It also makes a lot more possible: 
>
> let people = ["David", "Chris", "Joe", "Jordan", "Tony"]
> let winner = people.random()

Hey, that is pretty awesome!

-- 
-Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] How to be DRY on ranges and closed ranges?

2016-10-16 Thread Dave Abrahams via swift-users

on Wed Oct 12 2016, Jean-Denis Muys  wrote:

> Hi,
>
> I defined this:
>
> func random(from r: Range) -> Int {
> let from = r.lowerBound
> let to =  r.upperBound
>
> let rnd = arc4random_uniform(UInt32(to-from))
> return from + Int(rnd)
> }
>
> so that I can do:
>
> let testRandomValue = random(from: 4..<8)
>
> But this will not let me do:
>
> let otherTestRandomValue = random(from: 4...10)
>
> The error message is a bit cryptic:
>
> “No ‘…’ candidate produce the expected contextual result type ‘Range’”
>
> What is happening is that 4…10 is not a Range, but a ClosedRange.
>
> Of course I can overload my function above to add a version that takes a 
> ClosedRange.
>
> But this is not very DRY.
>
> What would be a more idiomatic way?

In our original design we had a common protocol to which open and closed
ranges conformed, and you could pass an instance of RangeProtocol.  That
was removed because the overall complexity was not a win, but I predict
it will come back for Swift 4:
https://github.com/apple/swift/pull/3737

But for what you want to do, you don't need anything that complicated:

protocol CompleteRange {
  associatedtype Bound : Comparable
  var lowerBound : Bound { get }
  var upperBound : Bound { get }
}

extension CountableRange : CompleteRange {}
extension CountableClosedRange : CompleteRange {}

import Darwin
func random(from r: R) -> Int where R.Bound == Int, R: 
Collection {
  let rnd = arc4random_uniform(numericCast(r.count))
  return r.lowerBound + Int(rnd)
}

print(random(from: -5..<5), random(from: -20...20))

Hope this helps,

-- 
-Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] UnsafeMutablePointer on the stack?

2016-10-02 Thread Dave Abrahams via swift-users

on Sun Oct 02 2016, Mike Ferenduros  wrote:

> You can use a local like this:
> var x: UInt32 = 0
> withUnsafePointer(to: x) { randomWordPT in
> //your existing code here
> }
>
> Or I'm not sure if small arrays go on the heap, but

They do.

> var bytes: [UInt8] = [0,0,0,0]
> _ = SecRandomCopyBytes(kSecRandomDefault, bytes.count, )
> return bytes.reduce(0) { ($0 << 8) | UInt32($1) }
>
> reads a little nicer.
>
> Personally I would be surprised if the malloc caused an actual measurable
> performance hit tbh.
>
> On Mon, 3 Oct 2016 at 02:15 Jean-Denis Muys via swift-users <
> swift-users@swift.org> wrote:
>
>> Hi,
>>
>> I have some issues using the new raw memory API. For instance, let's
>> suppose I want to call the `SecRandomCopyBytes` API to generate a
>> cryptographically secure random 32-bit number. The difficulty is its 3rd
>> argument, which is declared as UnsafeMutablePointer. Here is a
>> function that does that:
>>
>> func entropicRandom() -> UInt32 {
>>
>> let randomWordPT = UnsafeMutablePointer.allocate(capacity: 1)
>>
>>
>> let _ = randomWordPT.withMemoryRebound(to: UInt8.self, capacity: 4) {
>> (p: UnsafeMutablePointer) -> Int32 in
>>
>> let result = SecRandomCopyBytes(kSecRandomDefault, MemoryLayout<
>> UInt32>.size, p)
>>
>> return result
>>
>> }
>>
>> let randomInt32 = randomWordPT[0]
>>
>> randomWordPT.deallocate(capacity: 1)
>>
>> return randomInt32
>>
>> }
>>
>> apparently, the calls to allocate and then deallocate suggest that there
>> is some heap allocation happening behind the scene here, possibly
>> malloc/free. Is that correct?
>>
>> If so, this is quite wasteful. Is there a way to use a local variable on
>> the stack to achieve the same result?
>>
>> Thanks,
>>
>> Jean-Denis
>>
>>
>>
>> ___
>> swift-users mailing list
>> swift-users@swift.org
>> https://lists.swift.org/mailman/listinfo/swift-users
>>
> ___
> swift-users mailing list
> swift-users@swift.org
> https://lists.swift.org/mailman/listinfo/swift-users
>

-- 
-Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] A sample Rational number type

2016-10-02 Thread Dave Abrahams via swift-users

on Fri Sep 30 2016, Hooman Mehr  wrote:

> For anybody who is interested: This gist
> 
> contains a Rational number implementation for Swift 3.0. It is a
> single file that you can paste in a playground and take a look, or
> remove the last few lines and drop the file into your own module. The
> recommended way to create a rational number is specifying Rational
> type as in:
>
> let r: Rational = 18/64
> // or
> let x = 5 + 2/3 as Rational
>
> or use tolerance operator `±` to convert from floating point:
>
> let r2 = 2.109±0.0005 // 2⁷⁄₆₄

Presumably you mean:

  let r2 = r±0.0005 // turn a Rational into a Double with no more than
// .0005 rounding error

? That is supercute!

> Rational type conforms to AbsoluteValuable (hence Equatable,
> Comparable, ExpressibleByIntegerLiteral, SignedNumber), Strideable,
> and CustomStringConvertible.

Have you thought about what this would look like after we land
https://github.com/apple/swift/pull/3796 (see
https://github.com/apple/swift-evolution/blob/master/proposals/0104-improved-integers.md)
?

You can also find a working prototype of that code at
https://github.com/apple/swift/blob/b7622b41756e33bdf3f3415320ffec52aec73281/test/Prototypes/Integers.swift.gyb
It would be great to know that the protocols we've designed actually
work out for Rational numbers.  With these protocols, can you make your
Rational generic on the underlying integer type?

There's a BigInt implementation based on these protocols here:
https://github.com/natecook1000/swift/commit/45c52a75dcc15024649a5e093a5da4ee031595c2

It would be really cool to see it work with a generic version of your
Rational type.

> It always uses fully-reduced representation for simplicity and clarity
> of comparisons and uses LCM (lowest common multiple) for addition &
> subtraction to reduce the chance of overflow in the middle of
> computations. The disadvantage of these design choices are: It is not
> guaranteed to keep the nominator and denominator as specified during
> construction, and GCD / LCM computations reduce its performance.
>
> The performance trade-off is not huge and is usually acceptable for
> typical rational number use cases. Preserving denominator can be
> addressed with a number formatter for rational numbers that I will add
> later. GCD is computed with Stein's algorithm (binary GCD algorithm).

It's interesting to see that one wants a different algorithm for GCD
when using BigInts:
https://en.wikipedia.org/wiki/Binary_GCD_algorithm#cite_note-11

I wonder how that should be dispatched...

-- 
-Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] UnsafeMutablePointer on the stack?

2016-10-02 Thread Dave Abrahams via swift-users

on Sun Oct 02 2016, Jean-Denis Muys  wrote:

> Hi,
>
> I have some issues using the new raw memory API. For instance, let's
> suppose I want to call the `SecRandomCopyBytes` API to generate a
> cryptographically secure random 32-bit number. The difficulty is its 3rd
> argument, which is declared as UnsafeMutablePointer. Here is a
> function that does that:
>
> func entropicRandom() -> UInt32 {
>
> let randomWordPT = UnsafeMutablePointer.allocate(capacity: 1)
>
> let _ = randomWordPT.withMemoryRebound(to: UInt8.self, capacity: 4) {
> (p: UnsafeMutablePointer) -> Int32 in
>
> let result = SecRandomCopyBytes(kSecRandomDefault, MemoryLayout<
> UInt32>.size, p)
>
> return result
>
> }
>
> let randomInt32 = randomWordPT[0]
>
> randomWordPT.deallocate(capacity: 1)
>
> return randomInt32
>
> }
>
> apparently, the calls to allocate and then deallocate suggest that there is
> some heap allocation happening behind the scene here, possibly malloc/free.
> Is that correct?

Quite so.  

But what did you suppose allocate and deallocate did, if not dynamic
memory allocation?

> If so, this is quite wasteful. Is there a way to use a local variable on
> the stack to achieve the same result?

func entropicRandom() -> UInt32 {
  var randomInt32: UInt32 = 0
  let byteCount = MemoryLayout.size(ofValue: randomInt32)

  withUnsafeMutablePointer(to: ) {
$0.withMemoryRebound(to: UInt8.self, capacity: byteCount) {
  SecRandomCopyBytes(kSecRandomDefault, byteCount, $0)
}
  }
  return randomInt32
}

HTH,

-- 
-Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] CharacterSet vs Set

2016-10-02 Thread Dave Abrahams via swift-users

on Sun Oct 02 2016, Jean-Denis Muys  wrote:

> I was playing with CharacterSet, and I came up with:
>
> let vowels = CharacterSet(charactersIn: "AEIOU")

Yeah, because CharacterSet is a set of UnicodeScalars, not a set of
Character.  That should probably get fixed somehow.  I suggest filing a
radar against Foundation.

> let char: Character = "E"
>
> vowels.contains(char)
>
> That last line doesn't compile: I get "*cannot convert value of type
> 'Character' to expected argument type 'UnicodeScalar'*"
>
> The problem is, I could not find a simple way to convert from a character
> to a unicodeScalar. The best I found is the very ugly:
>
> vowels.contains(String(char).unicodeScalars[String(char).unicodeScalars.
> startIndex])
>
> Did I miss anything? 

  vowels.contains(String(char).unicodeScalars.first!)

> Does it have to be that horrific?

For now, I'm afraid I don't have anything better for you.  I very much
hope to improve String usability substantially for Swift 4.

> If so, I find using Set much better:
>
> let vowelsSet: Set = Set("AEIOU".characters)
>
> vowelsSet.contains(char)
>
> I must have missed something. Any suggestion welcome

-- 
-Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] Problem with COW optimization

2016-09-18 Thread Dave Abrahams via swift-users

on Sun Sep 18 2016, Adrian Zubarev  wrote:

> Dear Swift community,
>
> currently I’m building a value type XML library which is baked behind
> the scene with a reference type to manage graph traversing between
> nodes. I also like to COW optimize the xml graph, but I run into one
> single problem atm.
>
> Image this xml tree:
>
> 
> 
> 
> It’s just a root element with one single child. As for value types it
> should be totally fine to do something like this:
>
> // The given xml tree
> var root = XML.Element(name: "root")
> let item = XML.Element(name: "item")
> root.add(item)
>
> // The problematic behavior
> root.add(root)
> If this would be a simple value type without any references behind the
> scenes you could imagine that the result of the last code line will
> look like this:
>
> 
> 
> 
> 
> 
> 

Yep, that's exactly the right answer for a tree with value semantics.
The simplest way to implement this tree is to use an Array for the child
nodes.

> Basically we copied the whole tree and added it as the second child
> into the original root element.
>
> As for COW optimization this is a problem, just because the passed
> root is a copy of a struct that contains the exact same reference as
> the original root element. 

I don't understand why that's a problem.

> isKnownUniquelyReferenced() will result in false inside
> the add method.

...as it should.

> Is there any chance I could force my program to decrease the reference
> counter of that last item after I’m sure I don’t need it?!

Which last item?  When are you sure you don't need it?  What result do
you hope for?

> A few more details: inside the add method I’m always cloning the
> passed reference just because graphs aren’t that trivial and otherwise
> I could possibly end up with a cycle graph, which would be really
> bad. After that job I’m sure that I don’t need the passed reference
> anymore and I need a way to escape from it.
>
> I’d appreciate any suggestions and help. :)

It's not clear what you want to acheive nor can I picture the code
you're using to acheive it, so it's hard to give useful feedback.

Sorry,

-- 
-Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] Checking whether an object is uniquely referenced, using a weak reference to it

2016-09-18 Thread Dave Abrahams via swift-users

on Tue Jun 28 2016, Jordan Rose  wrote:

>> On Jun 27, 2016, at 18:52, Tim Vermeulen  wrote:
>> 
>> Thanks for your reply. It didn’t clear up everything, though. The
>> official documentation says "Weak references do not affect the
>> result of this function.”, which suggests that weak (and unowned)
>> references intentionally aren’t counted. The docs only mention the
>> implementation of copy-on-write behaviour as a use case (which also
>> happens to be what I’m using it for).
>
> I would expect that weak references are important to count for COW,
> since you can observe changes through them. Dave?

This sort of depends on what you expect the semantics of your weak
reference to be.  It's not possible to take a weak reference to an
Array; you can only take a weak reference to the NSArray it uses as a
backing store.  That's an Objective-C-only idea.

Given an arbitrary NSArray on the Objective-C side, it might turn out to
be an NSMutableArray, so if you want to avoid observing changes to it,
in principle you need to copy it.  So I think it's possible to argue
that the weak reference count is not an issue here.

-- 
-Dave
___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] Chaining struct-mutating funcs

2016-08-10 Thread Dave Abrahams via swift-users

on Tue Aug 09 2016, Fritz Anderson  wrote:

> I’m sending directly to those who took time over my question, because, per 
> Michael’s request, I have a
> minimal case to attach. Phrases in boldface are for skimmability, not 
> shouting. 
>
> Strip out my use case (I’m encouraged that Dave recapitulated exactly
> what I was asking about). My remaining question is: How do you safely
> reuse a class reference as the backing store for a struct?  Yes, it’s
> done all the time, but the trick requirement is that I want to chain
> the funcs that do it; chained value returns are immutable; and as far
> as I could tell, you can’t get CoW-safe reuse without mutating
> self. The result is that you are forced to make expensive copies of
> the backing store every time. Joe’s solution looked promising in that
> it purported to pass the CoW buffer (if possible) out of the func
> after doing all the mutation internally.
>
> I couldn’t figure out how the answer Joe gave could work: His code
> duplicates the struct’s original reference into a copy of the struct,
> after which he expects the runtime to report (when possible) that no
> such duplicate exists. I asked how this could be, as my attempt to
> replicate in a playground showed the reference was never found unique
> — which is what I had intuitively expected.

Well, a playground is a terrible way to check this, since lifetimes
don't necessarily obey the normal rules, but... you're right, it doesn't
seem to be workable today.

>
>
> He says this fundamental design pattern in Swift works only if you
> change the semantics of the language by turning on the
> optimizer. 

When you count performance characteristics as semantics, yes.

> (Sorry to be all Asperger's about it, but nobody corrected me the
> first time I put it this way.)

Actually I can't even get it to happen with the optimizer on in my
tests.

> I have many, many questions, I might even hazard objections, but
> they’re moot: Optimized or not, that code never reuses the backing
> object.
>
> The attached project was built with Xcode 8.0b5. It uses Joe’s code
> (except I still must use isUniquelyReferencedNonObjC(_:)). I run
> addInts(x:, y:) and check two ways whether the reference was found
> unique. Same result, optimized or not.
>
> It occurred to me that the globals s_x and s_y might bump the reference 
> count. I removed them and used this
> instead:
>
> let s_result = addInts(x: S(c: C(value: 99)), y: S(c: C(value: -98)))
>
> Still no unique references.
>
> I recognize I am taking up a lot of god time mere days before a major
> release, when the likeliest outcome is that I’m a jackass. 

I don't think so.  What's more likely is that we could be optimizing
better. 

> My concern runs deeper than what’s in this message, but I shouldn't
> muddy the waters.  Those deeper things can go back to the public once
> I understand the issue better (or you boot me back).
>
> ---
>
> Context (supplementary, no need to spend time)
>
> If seeing what I’m trying to do helps, I’ve attached my attempt. I’m
> sure there are defects in API style, safety, and correctness. I’d have
> done more if I hadn’t suspended the project over this issue. Class
> FloatBuffer is the backing store; ManagedFloatBuffer is the wrapper
> class that does all the operations. None of the operations are
> declared mutating.
>
> Anything that calls (unary|binary)Operator returns a fresh
> ManagedFloatBuffer every time; structs and their buffers are created
> and initialized every time — intentionally. It seems to work well
> under gentle use.
>
> Callers of mutabilityWrapper preserve the receiver’s backing buffer
> whenever possible and mutate it in-place.  Those funcs always return
> self. These might be a big win; I can’t tell because I’ve never been
> able to get unique references. Because there’s an allocation (possibly
> initialization) every time, they are no better than the
> (unary|binary)Operator funcs. malloc and friends take up a significant
> amount of time on the scale of vector math.
>
> Both flavors can cascade; the only problem is that the “in-place”
> methods don’t live up to the name.

The question of how to optimize the evaluation of non-mutating
expressions using in-place operations is an old one.  Once upon a time
we were pursuing language features for that purpose
(https://github.com/apple/swift/blob/master/docs/proposals/Inplace.rst)
but that particular approach is... an ex-approach ;-).

-- 
-Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] Extending a generic type where T == Void

2016-08-09 Thread Dave Abrahams via swift-users

on Tue Aug 09 2016, Benedict Cohen  wrote:

> I have an enum that represents the states of a task:
>
> enum TaskState{
> case preparing
> case ready(InType)
> case executing(InType, TaskIdentifier)
> case success(InType, OutType)
> case failure(InType, Error)
>
> mutating func transition(toReady: InType) {...}
>
> }
>
> //Usage
> var locationSearchTaskState: TaskState = .preparing
> //...
> locationSearchTaskState.transition(toReady: text)
>
> This works as desired for most cases. Not all tasks, however, have an input:
>
> var topLocationsTaskState = .ready( () )
>
> In this case we have to pass the empty tuple as the value which is ugly. I'd 
> like to add some sugar to make this nicer. Something along the lines of:
>
> extension TaskState where InType: Void {...}
>
> Of course this doesn't work because Void is not a protocol (nor can it
> conform to a protocol because it's just a tuple). So my question: How
> can I extend a generic type when the generic parameter is Void? Are
> there alternative ways to model this problem?

There's a horrible hack you can use:

protocol TaskStateProtocol {
  associatedtype InType
  mutating func transition(toReady: InType)
}
extension TaskState : TaskStateProtocol {}

extension TaskStateProtocol where InType == Void {
  // ... < put your stuff here
}


HTH,
-- 
-Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] Set size of byte array

2016-08-08 Thread Dave Abrahams via swift-users

on Fri Aug 05 2016, KS Sreeram  wrote:

>> On 05-Aug-2016, at 1:19 PM, Daniel Vollmer  wrote:
>> 
>> I’m by no means a Swift expert (not even a user at the moment), but I don't
>> see a way to do this either. The best that comes to mind is initializing a
>> ContiguousArray with the sufficient capacity as size, using
>> withUnsafeBufferPointer to overwrite elements, and then use replaceAll() with
>> an empty collection to remove the excess size.
>
> The only initializer that could help with this is:
> init(count:repeatedValue:). Unfortunately, this means the buffer is
> written to twice - once in the initializer, and a second time to
> actually fill in the data. It’s not efficient.
>
>> 
>> I'd think that just reserving enough capacity and then appending the elements
>> one-by-one will be (at least?) as efficient: The byte is always copied 
>> anyway,
>> and in this case you wouldn’t have to default-construct the capacity 
>> beforehand.
>
> This too isn’t efficient because each append call will incur an the
> cost of checking for sufficient capacity and also incrementing the
> size. The additional penalty could dwarf the cost of actually copying
> a byte! I don’t think the compiler is capable of removing this
> inefficiency.

Create a Sequence that represents the elements you're going to append,
e.g.:

  var a = [1, 2]
  a.reserve(256)
  a += sequence(first: 3, next: {$0 < 1000 ? ($0 + 3) * 2 : nil})

There are lots of ways to make Sequences, but the overloaded sequence()
functions are probably the easiest.

HTH,

-- 
-Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] Chaining struct-mutating funcs

2016-08-08 Thread Dave Abrahams via swift-users

on Fri Aug 05 2016, Joe Groff  wrote:

> Since your backing buffer is copy-on-write, you can do the in-place
> mutation optimization in your immutable implementations, something
> like this:
>
> class C {
>   var value: Int
>   init(value: Int) { self.value = value }
> }
>
> struct S { var c: C }
>
> func addInts(x: S, y: S) -> S {
>   var tmp = x
>   // Don't use x after this point so that it gets forwarded into tmp
>   if isKnownUniquelyReferenced() {
> tmp.c.value += y.c.value
> return tmp
>   } else {
> return S(c: C(value: tmp.c.value + y.c.value))
>   }
> }
>
> which should let you get similar efficiency to the mutating
> formulation while using semantically immutable values.

Yep, that works.  The only other trick I know of is to create a
composition of operations that you apply at the end with an operator:

pixelXes <- multiply(perspectiveCorrections).sin
speeds <- multiply(pixelXes)
  .multiply(feetToMeters)
  .subtract(cameraSpeed.mean)
let sumSquaredOfResiduals = speeds.sumOfSquares

HTH,

-- 
-Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] generic function called recursively not compiling

2016-08-07 Thread Dave Abrahams via swift-users

on Thu Aug 04 2016, Ray Fix  wrote:

> I filed rdar://27700622  and attached a playground.
> Any workaround magic I can do here?
>
> func quickSort(_ input: [Element]) -> [Element] {
> if input.count < 2 {
> return input
> }
> let pivot = input.first!
> let left = input.dropFirst().filter { $0 <= pivot }
> let right = input.dropFirst().filter { $0 > pivot }
>
> // Does not compile with (Swift 3pre) Xcode 8 b1,2,3,4
> // Does compile with (Swift 2.2) Xcode 7.3
> return quickSort(left) + [pivot] + quickSort(right)
> }
>
> quickSort([3,5,1,2])
>
> Error:
> //Playground execution failed: error: quicksort.playground:11:22: error: 
> cannot convert value of type '[Element]' to expected argument type '[_]'
> //return quickSort(left) + [pivot] + quickSort(right)
> // ^~~~
>
Hi Ray,

I don't know why, but the type checker is obviously falling over here.
This works around it:

  return quickSort(left) as [Element] + [pivot] + quickSort(right) 
 

HTH,
-- 
-Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] non-mutating func that still mutates a struct, compiler not aware

2016-08-06 Thread Dave Abrahams via swift-users

on Sat Aug 06 2016, Raphael Sebbe  wrote:

>> Those UnsafeMutablePointer(…) calls aren’t correct. When an array is
>> implicitly converted to a pointer in Swift, the pointer is only valid for
>> the *immediate* call that it’s being passed to. In this case, that’s the
>> UnsafeMutablePointer initializer, and after that the pointer is invalid. So
>> it’s possible that either the same space is being reused for both pointers,
>> or that it’s *not* uniquing the array because it thinks it only has to
>> make an UnsafePointer, or both.
>>
>> As Brent says, passing the arrays directly to the method using inout
>> semantics (&) should get you the behavior you want.
>>
>> (Yes, there should be a diagnostic for this. I’m pretty sure we have a bug
>> already, so no need to file. The Swift 3 pointer APIs make this a little
>> harder to do by accident, too.)

If you want to be safe in the general case, use 

  a.withUnsafe[Mutable]BufferPointer { let p = $0.baseAddress; ... }

which will force the pointer to remain valid through the execution of
the entire closure.  Yes, it's syntactically a *lot* heavier than just
passing , but it doesn't break without warning when some maintainer
comes along and passes  through a function.

We ought to prevent the  -> UnsafeMutablePointer conversion trick from
working except when calling imported C APIs directly.

-- 
-Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] Are value semantics really appropriate in a diagramming app?

2016-08-02 Thread Dave Abrahams via swift-users

on Tue Aug 02 2016, Rick Mann  wrote:

>> On Aug 2, 2016, at 13:07 , Dave Abrahams via swift-users 
>> <swift-users@swift.org> wrote:
>> 
>> 
>> on Mon Aug 01 2016, Rick Mann  wrote:
>> 
>
>>>> On Aug 1, 2016, at 19:18 , Jack Lawrence <ja...@apple.com> wrote:
>>>> 
>>>> Jens: Why? There are significant benefits to value semantics for
>>>> this type of problem, for the reasons laid out in the WWDC
>>>> videos. It would be helpful to know why you disagree in this
>>>> case—maybe there are solutions to the issues you’re thinking of.
>>>> 
>>>> Rick: I’d think that value semantics would be the right choice
>>>> here. When you do a mutation, you would copy the state of the entire
>>>> diagram. It should be efficient via COW, but if not you can
>>>> implement you own more fine-grained COW types with
>>>> isUniquelyReferenced(). This would allow you to easily support
>>>> things like undo.
>>> 
>>> The more I consider this, the more I think value semantics won't work
>>> for me. I think, to take advantage of the easy undo feature, my entire
>>> model *must* be implemented with value semantics.
>> 
>> That certainly helps.  You could introduce an explicit copy operation
>> to get around the use of classes, but that can get very messy.
>> 
>>> But my model has implicit reference semantics: multiple instances of a
>>> part can share a PartDefinition; it is intended that if the
>>> PartDefinition changes, all the referencing instances get the
>>> change. 
>> 
>> That is definitely a reference.  However, there are lots of ways to
>> represent references such that the entire model still has value
>> semantics.  Reference semantics, in the broadest sense, are everywhere:
>> as soon as you have an array and an integer, you have reference
>> semantics.  The problem with using classes is that they introduce
>> reference semantics *implicitly* and *prolifically*.
>> 
>> So, for example, if you are implementing a model and you want to
>> represent a selection as a separate data structure, then you'll need to
>> give every selectable element some kind of id, so you can store the ids
>> there. One way to do that is to store all your elements in an array in
>> your model, and use the index into the array as the id.  Then when one
>> element needs to refer to another element, it stores the ID of that
>> element.
>> 
>> [Aside: one of the simplest and most efficient representations of a
>> generalized graph structure is `[[Int]]`, which has value semantics.
>> Each element of the outer array corresponds to a vertex, and each
>> element an inner array represents the target of that vertex's outgoing
>> edges]
>> 
>> The most obvious thing you don't get from this kind of arrangement is
>> automatic lifetime management: an element doesn't disappear just because
>> you've stopped referring to it.  Whether that's appropriate for your
>> application or not is a question for you to answer.  
>> 
>> You can selectively recreate as much of the implicit behavior of classes
>> as you like, e.g. storing reference counts to recreate automatic
>> lifetime management and/or threading a free list through the array to
>> maintain ID stability, but of course at some point it becomes silly.
>> 
>> Where your particular application falls in this spectrum is for you to
>> say.  The fact that there's a component of reference semantics in your
>> model doesn't mean you can't use value types, and the fact that using
>> value types has some awesome benefits doesn't mean you can't use
>> classes.  Weigh the tradeoffs and make an informed choice.
>> 
>>> There are additional situations in which reference semantics are at
>>> play, as well: a PartDefinition can have one or more labels, but each
>>> instance can specify the relative location of the label for that
>>> instance. So, there is struct that contains a position and a reference
>>> to the label in the PartDefinition. But if the contents of the label
>>> changes, all the instances need to see that change.
>>> 
>>> I don't think I get to take advantage of value semantics, and it makes
>>> me wonder if any typical, non-trivial model's object graph really has
>>> no reference semantics.
>> 
>> Some do, but many-to-one relationships are an important concept, and
>> many applications need to represent them somehow.  I've personally found
>> that most such relationships

Re: [swift-users] Are value semantics really appropriate in a diagramming app?

2016-08-02 Thread Dave Abrahams via swift-users

on Mon Aug 01 2016, Rick Mann  wrote:

>> On Aug 1, 2016, at 19:18 , Jack Lawrence  wrote:
>> 
>> Jens: Why? There are significant benefits to value semantics for
>> this type of problem, for the reasons laid out in the WWDC
>> videos. It would be helpful to know why you disagree in this
>> case—maybe there are solutions to the issues you’re thinking of.
>> 
>> Rick: I’d think that value semantics would be the right choice
>> here. When you do a mutation, you would copy the state of the entire
>> diagram. It should be efficient via COW, but if not you can
>> implement you own more fine-grained COW types with
>> isUniquelyReferenced(). This would allow you to easily support
>> things like undo.
>
> The more I consider this, the more I think value semantics won't work
> for me. I think, to take advantage of the easy undo feature, my entire
> model *must* be implemented with value semantics.

That certainly helps.  You could introduce an explicit copy operation
to get around the use of classes, but that can get very messy.

> But my model has implicit reference semantics: multiple instances of a
> part can share a PartDefinition; it is intended that if the
> PartDefinition changes, all the referencing instances get the
> change. 

That is definitely a reference.  However, there are lots of ways to
represent references such that the entire model still has value
semantics.  Reference semantics, in the broadest sense, are everywhere:
as soon as you have an array and an integer, you have reference
semantics.  The problem with using classes is that they introduce
reference semantics *implicitly* and *prolifically*.

So, for example, if you are implementing a model and you want to
represent a selection as a separate data structure, then you'll need to
give every selectable element some kind of id, so you can store the ids
there. One way to do that is to store all your elements in an array in
your model, and use the index into the array as the id.  Then when one
element needs to refer to another element, it stores the ID of that
element.

[Aside: one of the simplest and most efficient representations of a
generalized graph structure is `[[Int]]`, which has value semantics.
Each element of the outer array corresponds to a vertex, and each
element an inner array represents the target of that vertex's outgoing
edges]

The most obvious thing you don't get from this kind of arrangement is
automatic lifetime management: an element doesn't disappear just because
you've stopped referring to it.  Whether that's appropriate for your
application or not is a question for you to answer.  

You can selectively recreate as much of the implicit behavior of classes
as you like, e.g. storing reference counts to recreate automatic
lifetime management and/or threading a free list through the array to
maintain ID stability, but of course at some point it becomes silly.

Where your particular application falls in this spectrum is for you to
say.  The fact that there's a component of reference semantics in your
model doesn't mean you can't use value types, and the fact that using
value types has some awesome benefits doesn't mean you can't use
classes.  Weigh the tradeoffs and make an informed choice.

> There are additional situations in which reference semantics are at
> play, as well: a PartDefinition can have one or more labels, but each
> instance can specify the relative location of the label for that
> instance. So, there is struct that contains a position and a reference
> to the label in the PartDefinition. But if the contents of the label
> changes, all the instances need to see that change.
>
> I don't think I get to take advantage of value semantics, and it makes
> me wonder if any typical, non-trivial model's object graph really has
> no reference semantics.

Some do, but many-to-one relationships are an important concept, and
many applications need to represent them somehow.  I've personally found
that most such relationships are best expressed explicitly, which allows
me to preserve value semantics of the whole system. YMMV, of course.

HTH,

-- 
-Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] Why does RangeReplaceableCollection require an empty initialiser?

2016-07-06 Thread Dave Abrahams via swift-users

on Wed Jul 06 2016, Austin Zheng  wrote:

> Would this require a swift-evolution review, since it's technically an API
> change? (removing the initializer requirement is something I am also
> interested in seeing...)

Yes.

-- 
Dave
___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] Why does RangeReplaceableCollection require an empty initialiser?

2016-07-06 Thread Dave Abrahams via swift-users

on Wed Jul 06 2016, Tim Vermeulen  wrote:

> RangeReplaceableCollection has three initialisers: init(), init(_:)
> and init(repeating:count:). The latter two are implemented using the
> empty initialiser. But why are these initialisers part of this
> particular protocol? As far as I can tell, no other methods of this
> protocol depend on these initialisers. The requirement of the empty
> initialiser makes it impossible to have a collection conform to this
> protocol that needs additional data for its initialisation.

This is an excellent point, and I think it may have been an oversight
that we made this a requirement.  Please open a bug and/or file a radar.
https://bugs.swift.org/secure/Dashboard.jspa 

Thanks!

> For instance, I was making an array that works with any Strideable
> indices, not just integers. A startIndex is needed for its
> initialisation, so I can’t really conform it to
> RangeReplaceableCollection. If I do it anyways (with a fatalError() in
> the required empty initialiser) everything seems to work just fine,
> except for the protocol’s three initialisers.
>
> Perhaps these initialisers should be moved to a (possible new)
> different protocol?


-- 
Dave

___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] Protocols, `mutating` and Value vs Reference Types.

2016-04-29 Thread Dave Abrahams via swift-users

on Fri Apr 29 2016, Hooman Mehr  wrote:

> Thank you very much for your response. I made the change in the gist. This 
> takes
> me back to the same error that forced my into duplication path:
>
> “Cannot assign through subscript: ‘self’ is immutable” for the object case.
>
> The gist is self contained if you want to compile it yourself.
>
> Is this some kind of bug or the expected behavior?

Looks like a bug to me!

>
>
>     On Apr 29, 2016, at 5:28 PM, Dave Abrahams via swift-users
> <swift-users@swift.org> wrote:
>
> on Fri Apr 29 2016, Hooman Mehr  wrote:
>
> Hi,
>
> I am designing APIs that need to support both reference (class/object)
> and value
> types. I am running into restrictions of `mutating` keyword in my
> protocols and
> this is causing a lot of duplication of code. In order to understand
> what I mean
> please take a look at this gist. 
>
> As you see, I have pairs of almost identical declarations: 
> KeyValueStore
> vs
> KeyValueStoreObject, and AnyDictionaryStore vs 
> AnyDictionaryStoreObject.
> This
> keeps rapidly growing as I am designing my APIs. Is there any sane way
> around
> this?
>
> protocol KeyValueStoreObject : class, KeyValueStore {}
> protocol AnyDictionaryStoreObject : class, AnyDictionaryStore {}
>
> would probably work for you.
>
> HTH,
>
> -- 
> Dave
>
> ___
> swift-users mailing list
> swift-users@swift.org
> https://lists.swift.org/mailman/listinfo/swift-users
>

-- 
Dave
___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users


Re: [swift-users] Trying to learn swift 3 renamification (as mattn calls it!)

2016-04-22 Thread Dave Abrahams via swift-users

on Thu Apr 21 2016, Erica Sadun  wrote:

> On Apr 21, 2016, at 2:23 PM, Ryan Lovelett 
> wrote:
>
> On Thu, Apr 21, 2016, at 04:13 PM, Erica Sadun wrote:
>
> On Apr 21, 2016, at 2:05 PM, Ryan Lovelett
>  wrote:
>
> On Thu, Apr 21, 2016, at 03:50 PM, Erica Sadun via swift-users
> wrote:
>
> On Apr 21, 2016, at 12:57 PM, Charles Lane via swift-users
>  wrote:
>
> While rebuilding some apps using the new development trunk
> build, I figured out the naming changes to just about
> everything but this:
>
> let string = "Here is a string"
>
> string.drawWithRect(CGRect(x: 10, y: 10, width: 200, 
> height:
> 200), options: .usesLineFragmentOrigin, attributes: attrs,
> context: nil)
>
> Can someone tell me what the ‘string.drawWithRect changed
> to?
>
> @available(iOS 7.0, *)
>
> public func draw(with rect: CGRect, options:
> NSStringDrawingOptions = [], attributes: [String : 
> AnyObject]? =
> [:], context: NSStringDrawingContext?)
>
> Erica would you mind discussing/explaining how you went about
> figuring out what this function signature was? It looked like you
> copied/pasted it from Xcode (based on the styling). Did you just
> know the function and go to its source?
>
> I clicked through to the UIKit module, from there to NSString
> extensions, and then looked for draw.
>
> Thank you
>
> Not personally a fan since "with" makes no sense for a 
> geometric
> boundary unlike in: or inRect:.
>
> -- E
>
> Sadly, I don't know any way to provide "your automatic translation offends my
> aesthetics" feedback.

Radars are the appropriate vehicle.  The framework owner can then do
explicit things to tune how the API appears.

-- 
Dave
___
swift-users mailing list
swift-users@swift.org
https://lists.swift.org/mailman/listinfo/swift-users