An abstract question, not related to any particular language:
If I have a function as follows
min(int, int) :: int
which returns the smallest value in an array, and
concat([int], [int]) :: [int]
which combines two arrays, how should I write a function like
minInArray([int]) :: Int
which returns the smallest element in an array, but where the ouput could be chained like so, even with an empty input array:
min(minInArray(array1), minInArray(array2)) == minInArray(concat(array1, array2))
In other words, is there any commonly-used neutral element which minInArray could return on empty input, which wouldn't mess up min()?
One option would be to return some neutral value like null or NaN if the array has no elements, and then if the min() function is run and one of the arguments is the neutral value, then you just return the min of the other array. Another option would be to return the closest value the language has to +Infinity if the array is empty; this works and does not require modifying min(), but does have the side effect of returning an infinite value sometimes when the minInArray() function is called. This infinite value could work as a truly neutral value that works with the default min() function, but it may cause some confusion if the minimum value in an array really is infinite.
minInArray(arr1) to return null if arr1 is empty.
min() should return only non-null values over null. Meaning min() will only return null if both parameters are null. Otherwise, it will return the minimum non-null value.
While thinking about the issue we've come to seemingly the only solution possible:
if an array is empty - we should return the maximum possible value for int to satisfy the condition.
Not that nice actually...
Just to add some perspectives (not that this is a duplicate of the listed questions) -
All of these throw errors of some kind when asked to calculate min of an empty list or array: Java, Scala, Python, numpy, Javascript, C#. Probably more, but that's as far as I looked. I'm sure there are some that don't, but I'd expect most of those to be languages which have traded understandability and clarity for speed.
This question is about a specific language, but has answers relevant to all languages.
Note here how one can get around the issue in something like Python.
For Haskell in particular, note the advice in this question.
And lastly here's a response for a more general case of your question.
In general, it is always most important for code to work, but a close second to that is it must be understandable to humans. Perhaps it doesn't matter for your current project, if you'll be the only one dealing with that function, but the last thing I'd expect when calling a 'get_minimum' function, is Int.MAX.
I understand it makes the coding simple, but I'd urge you to beware of code that is easy to write and tricky to understand. A little more time spent making the code easy to read, with as much as possible having an immediately obvious meaning, will always save much more time later on.
Related
The following is the code, actually, #arr0 and #arr1 are not equal, even after sorting, they are not equal, but why "eq" will be printed? at first, I thought about the return value of sort funtion, but it did return an array,so what's the reason?
my #arr0 = (1,2);
my #arr1 = ("a","b");
if ( (sort #arr0) ~~ (sort #arr1) ) {
print "eq\n";
};
[Note: All links to documentation in this answer are to the documentation for version 5.12.1. This ensures the answer is useful for the original poster - it might make it less useful for other people.]
It's important to realise that arrays and lists are not the same. This is one case where the behaviour is different.
It's also important to read the documentation for sort(), which starts by saying:
In list context, this sorts the LIST and returns the sorted list value. In scalar context, the behaviour of sort() is undefined.
There are two important things there. Firstly, in list context, sort() returns a list, not an array. And secondly, in scalar context, its behaviour is undefined.
Now let's look at the smartmatch documentation. That's a big table of left- and right-operands that I won't reproduce here. But note that it doesn't mention lists at all. So, almost certainly, smartmatch is calling sort() in scalar context and doing either a string or numeric comparison
on the results (one of the last few rows in the table).
But we know that sort()'s behaviour in scalar context is undefined. So who knows what value smartmatch is comparing. But I guess that whatever random value it is returning, it is (at least) returning the same random value for both of your lists. Which means they appear to be equal.
As you've said in a comment, it works when you save the sorted results in arrays and pass arrays to smartmatch. That's because arrays have special behaviours defined in the smartmatch table.
Arrays are not lists
Don't call sort() in scalar context
Update: As ThisSuitIsNotBlack mentions in the comments, smartmatch has been rather unstable since it was introduced in Perl 5.10. Its behaviour has been tweaked in pretty much every Perl release since then and its final form still isn't completely agreed. For that reason, I strongly discourage you from using it at all.
I'm familiar with the idea of a hash function but I'm unclear on how GLib's implementation is useful. I'll explain this with an example.
Suppose I have an expensive function that is recursive (somehow) on the positive real numbers in a weird way that depends on number theory (I'm a mathematician). Let's say I have an algorithm that needs to compute the function on some smallish-range of large numbers. Say [1000000000 - 1000999999].
I don't want to call my expensive function one million times, so I start memoizing values recursively. Then at each call I don't need to necessarily compute the whole function from scratch, I can hopefully remember any values of the function on the lower numbers (during my recursing) that I have already computed. Let's assume that the actual total number of calls at that first level of recursion is low. So that there are a lot of repeated values and memoizing actually saves you a lot of time.
This is my cartoony way of understanding why a hash table data structure is useful. What I don't get is how to do this without knowing exactly what keys I'll need in advance.
Since the recursive function is number theoretic in general I don't know which values it will take over and over again. So I'd like to just throw these in a bucket (hash table) as they pop out of recursive calls to my function
For GLib, it would seem that your (key,value) pairs are always pointers to data that you personally have to keep lying around somewhere. So if my function is computing for input x. I don't know how to tell if I've seen the value x before, the function g_hash_table_contains() for example needs a pointer, not the value x. So what's the use!?
I'm still learning so be kind. I'm familiar with coding in C, but haven't yet used hash tables in this language and I'm trying to do so and be adept at it with GLib but I just don't get this.
Let me take a dig at it to explain it.
First of all, if we are using hashmap, then we need [key, value] pair for sure as our input.
So as a user of hashmap, we have to be creative about choosing key, and it varies depending upon the usecase.
In your case, as far as I understood, you have a function which works on a range and gives you result. And when calculating, it uses memoization so that results of small problem, which constitutes the bigger problem, can be used.
So for example, your case, you can use string as your key where string will be [1000000009] which may use result of [1000999998] which may further use result of 1000999997 and so on, and you do not find results in hashmap, then you will calculate it and save it in hashmap.
In nutshell, as a user, we need to be creative about choosing keys.
The analogues to understand is how you would have done, if you have to think about choosing primary key of database.
Another example to think is how you would have thought about solving fibonacci(n) using the hashmap.
I read a solution in the original problem space during the INITSOLVE stage. Some multi-aggregated variables are ignored. I guess this is okay since their values can be inferred once other variables' values are fixed. However, the objective value of the read solution is now off.. since objective from those multi-aggregated variables are not included.. Is there anyway around this?
The objective coefficients of multi-aggregated variables are added to the variables of the active representation, so that the objective value of the solution should normally still be correct.
However, it can happen that the multi-aggregation was done by a dual argument, i.e., there might be solutions where the multi-aggregated variable is set to a different value, but you can still set it to the value given by the multi-aggregation without deteriorating the objective. Moreover, presolving might change bounds or fix variables based on this type of argument as well.
In this case, your solution might not "fit" into the presolved problem, but is "adjusted" to a solution with value not worse than your original solution. Is this the case? Is the objective value of the solution better?
Moreover, you should check the objective function value of the solution with SCIPgetSolOrigObj() in order to get the objective value in the original space, since the objective offset and factor can be changed during presolving.
Also, please check the values of the variables in the original problem to see how the solution differs from the one you read in.
I am asked to write pseudocode and analyze the running time of my function.
I am given 2 descending sorted arrays, and 1 integer k
and then asked to find out the kth largest number in the union of the 2 arrays.
I have run my code, as the assignment duedate is not passed yet, I cannot post the code here, I am sorry.
there are some flaws,
Question 1: I don't know if I need to handle scenarios like k>sum(arraylen(a & b))
, or scenario if given 2 arrays are empty... say if I had to, what return values should I use? -1? what if the k-th largest is -1 exactly....I am uncertain.
Question 2:
when I tried to get the length of array, I used sizeof(ArrayA)/4, (C++), my friend pointed out that:
- on one hand, sizeof might not be a component of pseudocode, so I might need to use like ArrayA.length()
- on the other hand, if I use length(), it will make my algorithm take O(n) instead of O(k), as array need to go through itself completely to get the length. Is his point true? if it is, how should I modify my code so that it would possible be O(k) ?
Help please,
I appreciate any help. thanks a lot.
Remember that you're using pseudocode; Pseudocode should not look like C++.
You should try to use as much information as has been given in the assignment or in class and make as few assumptions as possible. In my experience of writing pseudocode for school assignments, it is acceptable to assume that getting the length of an array is O(1) time.
It would be nice if your assignment told you a range for k, but if it hasn't you should check cases as you've mentioned. I think it is acceptable to raise an exception if k is invalid. Either that or you can mention that behaviour of the program has not been specified for certain cases. Generally how you specifically handle cases that are not mentioned in the assignment is not too critical, but it definitely looks good to handle them in some way.
I don't understand the rationale behind the decision of this part of Lua. Why does indexing start at 1? I have read (as many others did) this great paper. It seems to me a strange corner of a language that is very pleasant to learn and program. Don't get me wrong, Lua is just great but there has to be an explanation somewhere. Most of what I found (on the web) is just saying the index starts at 1. Full stop.
It would be very interesting to read what its designers said about the subject.
Note that I am "very" beginner in Lua, I hope I am not missing something obvious about tables.
Lua is descended from Sol, a language designed for petroleum engineers with no formal training in computer programming. People not trained in computing think it is damned weird to start counting at zero. By adopting 1-based array and string indexing, the Lua designers avoided confounding the expectations of their first clients and sponsors.
Although I too found them weird at the beginning, I have learned to love 0-based arrays. But I get by OK with Lua's 1-based arrays, especially by
using Lua's generic for loop and the ipairs operator—I can usually avoid worrying about just how arrays are indexed.
In Programming in Lua's first discussion of tables, they mention:
Since you can index a table with any value, you can start the indices of an array with any number that pleases you. However, it is customary in Lua to start arrays with 1 (and not with 0, as in C) and several facilities stick to this convention.
Later on, in the chapter on data structures, they say almost the same thing again: that Lua's built-in facilities assume 1-based indexing.
Anyway, there are a couple conveniences to using 1-based indexing. Namely, the # (length) operator: t[#t] access the last (numeric) index of the table, and t[#t+1] accesses 1 past the last index. To someone who hasn't already been exposed to 0-based indexing, #t+1 would be more intuitive to move past the end of a list. There's also Lua's for i = 1,#t construct, which I believe falls under the same category as the previous point that "1 to the length" can be more sensible than indexing "0 to the length minus 1".
But, if you can't break the mindset of 0-based indexing, then Lua's 1-based indexing can certainly be more of a hindrance. Ultimately, the authors wanted something that worked for them; and I'll admit I don't know what their original goal was, but it's probably changed since then.
My understanding is that it's that way just because the authors thought it would be a good way to do it, and after they rolled the language out to the public that decision calcified considerably. (I suspect there would be hell to pay were they to change it today!) I've never seen a particular justification beyond that.
Perhaps a less significant point, but one I haven't heard mentioned yet: there is better symmetry in the fact that the first and last characters in a string are at 1 and -1 respectively, instead of 0 and -1.
Lua libraries prefer to use indices which start at 1. However, you can use any index you want. You can use 0, you can use 1, you can use -5. It is even in their manual, which can be found at (https://www.lua.org/pil/11.1.html).
In fact, something cool here is internal lua libraries will treat SOME passed 0's as 1's. Just be cautious when using ipairs.
So that: ("abc"):sub(0,1) == "a" and ("abc"):sub(1,1) == "a" will be true.
You can start an array at index 0, 1, or any other value:
-- creates an array with indices from -5 to 5
a = {}
for i=-5, 5 do
a[i] = 0
end
The specific definitions of array index in C and Lua, are different.
In C array, it means: item address offset of the array address.
In Lua array, it means: the n-th item in array.
Why most languages use 0-based index? Because the compiler code with offset definition is more convenient and effective. They mostly handle addresses.
And the Lua. This is the code of lua 5.3.5 for table index with C:
const TValue *luaH_getint (Table *t, lua_Integer key) {
if (l_castS2U(key) - 1 < t->sizearray)
return &t->array[key - 1];
else {
Node *n = hashint(t, key);
for (;;) {
if (ttisinteger(gkey(n)) && ivalue(gkey(n)) == key)
return gval(n);
else {
int nx = gnext(n);
if (nx == 0) break;
n += nx;
}
}
return luaO_nilobject;
}
}
We should focus on the code &t->array[key - 1], it have a subtraction operation. It is not effective compared with 0-based index.
But, the 1-based index is more neared with human being languages. We focus more on n-th item in English, Chinese, Japanese and also.
So, I guess the Lua designers choose 1-based index, they choose easy understanding for pure newer of program, give up the convenience and effectiveness.
In your example, table[0] will always return nil(null), unless you assign value to it yourself, like table[0] = 'some value' and then table[0] will return 'some value', which you assigned.
Here's an example:
tbl = {"some"}
print("tbl[0]=" .. tostring(tbl[0]))
print("tbl[1]=" .. tostring(tbl[1]))
nothing = {}
print("nothing[0]=" .. tostring(nothing[0]))
print("nothing[1]=" .. tostring(nothing[1]))
nothing[0] = "hey"
print("(after assign)\nnothing[0]=" .. tostring(nothing[0]))
The real reason is that the language is an implementation of the definition in a law of Portugal and the major development centre was in Brazil and their preference is to avoid the use of zero or empty or nothing as an index or subscript. However the language does permit the use of a start index other than 1 in a table creating function in some versions.
It makes sense to everyone, that if
table = {}
table is empty. So, when
table == {something}
The table contains something so what it contains is index 1 in table, if you know what I mean.
What I meant is that table[0] exists, and its table = {}, which is empty, now a programmer won't call a empty table, it sets them, and then fills it, it will be useless to find an empty table every time you want to call it, so it's simpler to just create an empty table.