How do I express the "OR" logic operator in Objective-C? - objective-c

Let's say that I want to check that one of two terms are effective, how do I express it?
if (value == 1 **--OR--** value == nil) {
do something;
}

||
eg: if (value == 1 || value == nil)

Related

Operator '==' cant be applied to 'Boolean' and 'Char'

So i want to compare three members of an array with as little code as possible. Heres what i did:
for(i in 0..2) {
if(board[i][0] == board[i][1] == board[i][2]) {
return true
} else if(board[0][i] == board[1][i] == board[2][i]) {
return true
}
}
(All of the values ar Char's FYI) But it didnt work. I get this error message "Operator '==' cant be applied to 'Boolean' and 'Char'". I also tried using .equals, but that just didnt work. Any ideas on what to do?
You can write a small function to keep it more readable and tidy, especially if You need to do that comparison often:
fun allEqual(vararg items: Any) : Boolean {
for(i in 1..(items.size-1)){
if(items[0] != items[i]) return false
}
return true
}
And invoke simply by comma separating values:
allEqual(board[i][0], board[i][1], board[i][2])
I don't know Kotlin specifically, but most* languages don't allow you to compare 3 values at the same time. What your error message is communicating is that your code ends up comparing
"Is board[i][0] equal to board[i][1]?" which is true/false (Boolean)
to
board[i][2], which is a Char.
*I don't know of any, but maybe there's one out there that does.
You have included this condition:
if(board[i][0] == board[i][1] == board[i][2])
Firstly, this one is compared: board[i][1] == board[i][2]
After comparing, it returns true. After that if logic converts to:
if(board[i][0] == true)
Now, board[i][0] is a char and you are trying to compare it to a boolean which is not possible. That's why you are getting this error.
You have to change the logic to:
if((board[i][0] == board[i][1]) && (board[i][1] == board[i][2]))
So, your code will be:
for(i in 0..2) {
if((board[i][0] == board[i][1]) && (board[i][1] == board[i][2])) {
return true
} else if((board[0][i] == board[1][i]) && (board[1][i] == board[2][i])) {
return true
}
}
Another approach:
for (i in 0..2) {
if (board[i].toSet().size == 1)
return true
else if (board.map { it[i] }.toSet().size == 1)
return true
}
As the others said, your first comparison returns Boolean, and the second compares Boolean to Char.
You can use an extension function, and transitivity to simplify things:
fun Any.equalsAll(vararg others: Any):Boolean
{
others.forEach {
if(it!=this)
return false
}
return true
}
and call:
if (board[0][i].equalsAll(board[1][i], board[2][i]))

More efficient way to write conditionals with lots of OR operators

How can I (more) efficiently write out an if / else conditional that uses the same variable and a huge amount of OR operators?
I've been banging my head on the desk trying to think of a way around writing out all of these OR operators with the same comparison. For loops won't do the trick, and I'm pretty certain that a do / while loop wouldn't do it either. A switch / case might solve this, but I don't think it could condense the code or make it any less tedious to write out.
The example below illustrates my dilemma. The uicollectionview API has a protocol method which is called for each section in the collection and needs a return value for the number of items in that section. Essentially, the protocol method below is a fancy for loop.
- (NSInteger)collectionView:(UICollectionView *)collectionView numberOfItemsInSection:(NSInteger)section {
if (section == 0 || section == 31) return 7;
else if (section == 1 || section == 26 || section == 27 || section == 28 || section == 29 || section == 30) return 6;
else if (section == 2 || section == 3 || section == 4 || section == 5 || section == 6 || section == 7 || section == 8 || section == 9 || section == 10 || section == 11 || section == 12 || section == 13 || section == 14 || section == 15) return 2;
else if (section == 16 || section == 17 || section == 18 || section == 19 || section == 20 || section == 21 || section == 22 || section == 23 || section == 24 || section == 25) return 4;
else return 7;
}
As you can see in the extremely tedious if / else conditional I've written, it checks for every single section. I feel like I'm missing something - that Objective-C provides a nifty way around this kind of tedious and inefficient conditional writing / checking?
A clean way is to use a switch statement. These are usually implemented with a branching array, so are quite efficient.
switch (section)
{
case 0:
case 31:
return 7;
...
}
And the most efficient of all (branchless) is a lookup-table:
const int nums[]= { 7, 6, 2, 2, 2... };
return nums[section];
switch is probably the right answer, but you can also use shift/mask, something like:
int sectionBit = 0x00000001 << section;
if (sectionBit & 0x80000001) return 7;
if (sectionBit & 0x7c000002) return 6;
etc
The disadvantage of this approach is that it's tedious and error-prone to define the bit constants, but one can sometimes develop the constants by using enums, etc (at the expense of long declaration strings).
A generic approach to this is to use NSArray / NSDictionary to build indexes, something like:
NSArray *sections = #[#3, #5, #27, ...];
if ([sections containsObject:#3]) ...
or
NSDictionary *sections = #{ #5: #27, #7: #23, ... };
int value = [sections[#(section)] intValue]

Why is this 'if' statement failing? [duplicate]

This question already has answers here:
Comparing Strings in Cocoa
(5 answers)
Closed 9 years ago.
I am trying to determine if I have a duplicate record in CoreData using MagicalRecord. To do that, I am comparing the updated data with the first existing record:
This is the code I am using to do the search:
// set up predicate to find single appointment
if(selectedApptKey.length > 0) {
NSPredicate *predicate = ([NSPredicate predicateWithFormat:
#"((aApptKey == %#) && (aStartTime == %#) && (aEndTime == %#) && (aServiceTech == %#))",
selectedApptKey, tStartDate, tEndDate, tStaff]);
NSLog(#"\n\nselectedApptKey: %#\ntStartDate: %#\ntEndDate: %#\ntStaff: %#",selectedApptKey, tStartDate, tEndDate, tStaff);
ai = [AppointmentInfo MR_findFirstWithPredicate:predicate inContext:localContext];
if((ai.aApptKey == selectedApptKey) &&
(ai.aStartTime == tStartDate) &&
(ai.aEndTime == tEndDate) &&
(ai.aServiceTech == tStaff)) {
updateFlag = YES;
}
}
This is the predicate data I am using to search for an existing record:
selectedApptKey: RolfMarsh3911
tStartDate: 2013-12-29 20:15:00 +0000
tEndDate: 2013-12-29 22:15:00 +0000
tStaff: Kellie
This is the resulting record as obtained from the above code:
Printing description of ai:
<NSManagedObject: 0xb705430> (entity: AppointmentInfo; id: 0xb7bca00 <x-coredata://649CD00C-3C88-4447-AA2B-60B792E3B25F/AppointmentInfo/p22> ; data: {
aApptKey = RolfMarsh3911;
aEndTime = "2013-12-29 22:15:00 +0000";
aImage = nil;
aNotes = "";
aPosH = 200;
aPosW = 214;
aPosX = 0;
aPosY = 231;
aServiceTech = Kellie;
aServices = "";
aStartTime = "2013-12-29 20:15:00 +0000";
client = nil;
})
As you can see, the record and search data are exact. Qustion is: why is the if statement failing (the updateFlag is not being set to YES)?
You need to use isEqualToString: instead of ==, since you want to compare the actual object values, not the pointers. Assuming these are all strings. If you have some date objects use isEqualToDate:.
== always compares the pointers, which in this case are not equal, since they are pointing to different objects.

IF-Statement ignores last criteria

So I have a bunch of input textfields to calculate some stuff. These are doubles. I want that every time its not all filled in, it will display "Please enter all values" Below mentioned code does this for all fields, except the last one, here nitrogen. If i change them around to make another variable last this does not work. Instead it just makes the app give the result when the last field is entered.
So for example, no fields got a value, but when I type something into nitrogen it gives me the result. If I type something else into any of the other fields (Nitrogen blank) i get the correct message "Please enter all values."
How do I make it account for all fields, not just all except the last one?
if (temprature,methane,ethane,propane,nbutane,ibutane,oxygen,npetane,ipetane,nhexane,nitrogen == 0)
{
outputText.text = #"Please enter all values";
} else
{
outputText.text = resultString;
}
Try this, this should work if any of the fields are empty.
if (temprature == 0 || methane == 0 || ethane == 0 || propane == 0 || nbutane == 0 || ibutane == 0 || oxygen == 0 || npetane == 0 || ipetane == 0 || nhexane == 0 || nitrogen == 0)
{
outputText.text = #"Please enter all values";
} else
{
outputText.text = resultString;
}

How do I make AND or OR expressions?

I wrote this:
if( a == -11 && b == -1 ){
{
if( a == -1) AND ( b == -1)...
But neither work, and I have the same problem with OR. How do I write expressions that include OR or AND?
You use && for “and”, and || for “or”.
(a == -11 && b == -1) is fine and correct. Objective-C uses all of the same logical operators as C. || is the logical-or operator.
if (a==-11 && b==-1) {
if perfectly legal in C, and therefore Objective-C.
Your second example is not C or Objective-C