How to call a function with variable number of arguments from JavaScript, defined eg. like this?
setIntValues(int... values)
(the example is from android.animation.ObjectAnimator object)
You pass the arguments as an array:
obj.setIntValues([0,5]);
For defining a type, in overloaded functions you can use:
var arr = Array.create("int",2);
arr[0] = 0;
arr[1] = 5;
obj.setIntValues(arr);
if you're using javascript:
var arr = [1,2,3];
setIntValues.apply(undefined, arr);
if you're using typescript:
const arr = [1,2,3];
setIntValues(...arr);
Related
I'm sorting an Array like this:
var users = ["John", "Matt", "Mary", "Dani", "Steve"]
func back (s1:String, s2:String) -> Bool
{
return s1 > s2
}
sorted(users, back)
But I'm getting this error
'sorted' is unavailable: call the 'sort()' method on the collection
What should be the correct way to use the sort() method here?
Follow what the error message is telling you, and call sort on the collection:
users.sort(back)
Note that in Swift 2, sorted is now sort and the old sort is now sortInPlace, and both are to be called on the array itself (they were previously global functions).
Be careful, this has changed again in Swift 3, where sort is the mutating method, and sorted is the one returning a new array.
Another way to use closure is:
var numbers = [2,4,34,6,33,1,67,20]
var numbersSorted = numbers.sort( { (first, second ) -> Bool in
return first < second
})
Another way is to use closure in a simple way:
users.sort({a, b in a > b})
In swift 2.2 there are multiple ways we can use closures with sort function as follows.
Consider the array
var names:[String] = ["aaa", "ddd", "rrr", "bbb"];
The different options for sorting the array with swift closures are as added
Option 1
// In line with default closure format.
names = names.sort( { (s1: String, s2: String) -> Bool in return s1 < s2 })
print(names)
Option 2
// Omitted args types
names = names.sort( { s1, s2 in return s1 > s2 } )
print(names)
Option 3
// Omitted args types and return keyword as well
names = names.sort( { s1, s2 in s1 < s2 } )
print(names)
Option 4
// Shorthand Argument Names(with $ symbol)
// Omitted the arguments area completely.
names = names.sort( { $0 < $1 } )
print(names)
Option 5
This is the most simple way to use closure in sort function.
// With Operator Functions
names = names.sort(>)
print(names)
var array = [1, 5, 3, 2, 4]
Swift 2.3
let sortedArray = array.sort()
Swift 3.0
let sortedArray = array.sorted()
My challenge is twofold:
To pick individual strings from an array of similar strings, but only if a boolean test has been passed first.
"Finally" I need to concatenate any/all of the strings generated into one complete text and the entire code must be in Swift.
Illustration: A back of the envelope code for illustration of logic:
generatedText.text =
case Int1 <= 50 && Int2 == 50
return generatedParagraph1 = pick one string at RANDOM from a an array1 of strings
case Int3 =< 100
return generatedParagraph2 = pick one string at RANDOM from a an array2 of strings
case Int4 == 100
return generatedParagraph3 = pick one string at RANDOM from a an array3 of strings
...etc
default
return "Nothing to report"
and concatenate the individual generatedParagraphs
Attempt: Code picks a random element within stringArray1, 2 and 3.
Example of what the code returns:
---> "Sentence1_c.Sentence2_a.Sentence3_b."
PROBLEM: I need the code to ONLY pick an element if it has first passed a boolean. It means that the final concatenated string (concastString) could be empty, just contain one element, or several depending on how many of the bools were True. Does anyone know how to do this?
import Foundation
var stringArray1 = ["","Sentence1_a.", "Sentence1_b.", "Sentence1_c."]
var stringArray2 = ["","Sentence2_a.", "Sentence2_b.", "Sentence2_c."]
var stringArray3 = ["","Sentence3_a.", "Sentence3_b.", "Sentence3_c."]
let count1 = UInt32(stringArray1.count)-1
let count2 = UInt32(stringArray2.count)-1
let count3 = UInt32(stringArray3.count)-1
var randomNumberOne = Int(arc4random_uniform(count1))+1
var randomNumberTwo = Int(arc4random_uniform(count2))+1
var randomNumberThree = Int(arc4random_uniform(count3))+1
let concatString = stringArray1[randomNumberOne] + stringArray2[randomNumberTwo] + stringArray3[randomNumberThree]
Okay, I didn't pass a Bool, but I show concatenating three random strings from a [String]. I ran this in a playground.
import Foundation
var stringArray = [String]()
for var i = 0; i < 100; i++ {
stringArray.append("text" + "\(i)")
}
func concat (array: [String]) -> String {
let count = UInt32(stringArray.count)
let randomNumberOne = Int(arc4random_uniform(count))
let randomNumberTwo = Int(arc4random_uniform(count))
let randomNumberThree = Int(arc4random_uniform(count))
let concatString = array[randomNumberOne] + array[randomNumberTwo] + array[randomNumberThree]
return concatString
}
let finalString = concat(stringArray)
I'm trying to rewrite example from classic book "JavaScript: The Good Parts" in CoffeeScript via list comprehensions:
var parse_url = /^(?:([A-Za-z]+):)?(\/{0,3})([0-9.\-A-Za-z]+)
(?::(\d+))?(?:\/([^?#]*))?(?:\?([^#]*))?(?:#(.*))?$/;
var url = “http://www.ora.com:80/goodparts?q#fragment”;
var result = parse_url.exec(url);
var names = ['url', 'scheme', 'slash', 'host', 'port', 'path', 'query', 'hash'];
var blanks = ' ';
var i;
for (i = 0; i < names.length; i += 1) {
document.writeln(names[i] + ':' +
blanks.substring(names[i].length), result[i]);
}
I can't get how to write loop and stuck with this code:
console.log "#{name}: " for name in names
I imagine you are trying to do something Like this
parse_url = /^(?:([A-Za-z]+):)?(\/{0,3})([0-9.\-A-Za-z]+)(?::(\d+))?(?:\/([^?#]*))?(?:\?([^#]*))?(?:#(.*))?$/
url = 'http://www.ora.com:80/goodparts?q#fragment'
result = parse_url.exec(url)
names = ['url', 'scheme', 'slash', 'host', 'port', 'path', 'query', 'hash']
alert "#{names[i]}: #{result[i]}" for i in [0..names.length-1]
In case someone comes here actually needing to iterate two arrays at the same time, this works:
for [course_event, remote_event] in zip(course.events, remote.events)
course_event.lessons = remote_event.lessons if event.lessons_need_updating
zip() is from here:
zip = () ->
lengthArray = (arr.length for arr in arguments)
length = Math.min(lengthArray...)
for i in [0...length]
arr[i] for arr in arguments
I have an example class such as:
class Foo
{
Int32 A;
IEnumerable<Int32> B;
}
Is it possible to transform an enumerable of Foo to an enumerable of Int32, which would include the A and the contents of B from all Foo's?
A non-LINQ solution would be:
var ints = new List<Int32>();
foreach (var foo in foos) {
ints.Add(foo.A);
ints.AddRange(foo.B);
}
The closest I could think of is:
var ints = foos.SelectMany(foo => var l = new List { foo.A }; l.AddRange(foo.B); return l);
But I wonder if there is a better solution that creating a temporary list?
This should work:
var results = foos.SelectMany(f => f.B.Concat(new[] { f.A}));
Basic approach is to create a new enumeration with one element by creating an array with one element which is f.A, concatenating this to the existing enumeration of f.B and finally flatten the sequence with SelectMany()
as a List<Int32> per your non-Linq example
var ints = Foo.B.ToList().Add(Foo.A);
Lazy more Linq-ish solution
var ints = Foo.B.Concat(new Int32[] {Foo.A})
var ints = foos.SelectMany(f => f.B.Concat(new int[] { f.A}));
If you specifically need f.A before all elements from f.B:
var ints = foos.SelectMany(f => (new int[] { f.A }).concat(f.B));
I have a 2D array which I want to send to a php page with $.ajax.
This is the code which creates the array:
for (var i = 0; i<rowlen; i++) {
if (breakcheck) {
break;
}
for (var j = 0; j<=columnlen; j++) {
thtext = columnheads.eq(j).text();
current_td = $(newrows[i]).find("td").eq(j);
if (current_td.find("input").length >0) {
rowdata[i,thtext] = current_td.find("input").val().trim();
if (rowdata[i,thtext] =='') {
alert("You must complete all fields");
breakcheck = true;
break;
}
} else {
rowdata[i,thtext] ='nada';
}
}//inner loop
}//outer loop
The array is filled properly with the nested loops and the I use JSON.stringify to format it. However when the ajax call is made all that is sent is an empty object ([]). What's wrong?
I might be wrong, but arr[i,j] is not the way to use multidimensional arrays in C-style languages. That would be arr[i][j].
IMHO what arr[i,j] will do is function as comma operator and use only j as an index.
OK I solved this by declaring r as an object (var r = {}) instead of declaring it as an array (var r = []). Thanks for the help.