String Comparison Not working Arduino - string

Could somebody explain what is wrong with this code. WHY is the if statement always false when it is matching the exact strings..I have tried it with == as well..Still, every time I am getting No Match Found !!.
String inData = "";
char inChar;
String property;
String a = "test";
void loop() {
Serial.println("String Comparison");
if(Serial.available() > 0){
while(Serial.available()>0) {
inChar = Serial.read();
inData.concat(inChar);
}
//Extracting Property
property = inData.substring(inData.lastIndexOf(":")+2); // Extracts the String "test"
Serial.println("Property:" +property);
if(property.equals(a)){ // It never matches though, it is TRUE all the time
Serial.println(" Matched !! ");
}
else
Serial.println(" Match Not Found !! ");
inData = "";
}
delay(5000);
}

Since I am able to see matches match and misses miss I think I need more information to replicate the error.
Since I don't see it happening I would guess it has to do with whatever the input is and how this line parses it.
property = inData.substring(inData.lastIndexOf(":")+2); // Extracts the String "test"
What is the current input that is failing?
Can you include your printed output with that input?
Add a line to print out property.length() to test for hidden whitespace characters

Related

charAt not working for strings from a file

Im using the charAt function to find the first and second letters in a string that was read from a file but after getting the first character from the charAt(0) line, charAt(1), throws an exection that the string is too short when I know it is not. Here is the code.
while(inputFile.hasNext()){
//read file first line
String line = inputFile.nextLine();
//if the first 2 letters of the line the scanner is reading are the same
//as the search letters print the line and add one to the linesPrinted count
String lineOne = String.valueOf(line.charAt(0));
String lineTwo = String.valueOf(line.charAt(1));
String searchOne = String.valueOf(search.charAt(0));
String searchTwo = String.valueOf(search.charAt(1));
if (lineOne.compareToIgnoreCase(searchOne) == 0 && lineTwo.compareToIgnoreCase(searchTwo) == 0){
System.out.println(line);
linesPrinted++;
}
}
I've tried checking the make sure the string isn't being changed after the charAt(0) use by printing and I know it isn't and I've run the program with no probems after just removing the line so I am sure it is this that's causing the problem
The only functional change needed would to change hasNext to hasNextLine.
As one might encounter a line shorter than 2, say an empty line at the end of file, check the length.
while (inputFile.hasNextLine()) {
// read file next line
String line = inputFile.nextLine();
if (line.length() < 2) {
continue;
}
// if the first 2 letters of the line the scanner is reading are the same
// as the search letters print the line and add one to the linesPrinted count
String lineOne = line.substring(0, 1);
String lineTwo = lin.substring(1, 2);
String searchOne = search.substring(0, 1);
String searchTwo = search.substring(1, 2);
if (lineOne.equalsIgnoreCase(searchOne) && lineTwo.equalsIgnoreCase(searchTwo)) {
System.out.println(line);
linesPrinted++;
}
}
There is a problem with special chars and other languages, scripts. A Unicode code point (symbol, character) can be more than one java char.
while (inputFile.hasNextLine()) {
// read file next line
String line = inputFile.nextLine();
if (line.length() < 2) {
continue;
}
// if the first 2 letters of the line the scanner is reading are the same
// as the search letters print the line and add one to the linesPrinted count
int]} lineStart = line.codePoints().limit(2).toArray();
int]} searchStart = search.codePoints().limit(2).toArray();
String lineKey = new String(lineStart, 0, lineStart.length);
String searchKey = new String(searchStart, 0, searchStart.length);
if (lineKey.equalsIgnoreCase(searchKey)) {
System.out.println(line);
linesPrinted++;
}
}

Program to find if a string is a palindrome keeps on failing. Even after using toLowerCase() command for both strings, output doesn't come

import java.util.Scanner;
class Palindrome_string
{
public static void main()
{
System.out.println("\f");
Scanner sc = new Scanner(System.in);
System.out.println("Enter a string");
String a = sc.nextLine();
int b = a.length();
String rev = "";
for (int i = b - 1; i >= 0; i--)
{
char c = a.charAt(i);
rev = rev + c;
}
System.out.println("Original word "+a);
System.out.println("Reversed word "+rev);
a = a.toLowerCase();
rev = rev.toLowerCase();
if (a == rev)
{
System.out.println("It is a palindrome");
}
else
{
System.out.println("It is not a palindrome");
}
sc.close();
}
}
The program compiles properly. Still, when running the program, the message which tells if it is a palindrome prints incorrectly. What changes do I make? Here is a picture of the output. Even though the word 'level' (which is a palindrome) has been inputted, it shows that it isn't a palindrome. What changes should I make? output pic
You should not use == to compare two strings because it compares the reference of the string, i.e. whether they are the same object or not.
Use .equals() instead. It tests for value equality. So in your case:
if (a.equals(rev))
{
System.out.println("It is a palindrome");
}
Also try not to use single-letter variable names except for index variables when iterating over a list etc. It's bad practice.

Get String Between 2 Strings with Arduino

I am looking for a way to get a String between 2 Strings using Arduino. This is the source String:
Hello, my name is John Doe# and my favourite number is 32#.
The output has to be:
String name = "John Doe"; //Between "name is " and "#"
String favouriteNumber = "32"; //Between "number is " and "#"
How can this be achieved with Arduino?
I am not able to find any information online about this. Those examples for C are not working anyway. I understand that using String is not recommended in Arduino, but I have to do it this way to make things simpler.
By the way, this method of using a '#' to indicate the end of the data is not an ideal way to do it as I would like the input to be more human readable and more natural. Would anyone please suggest another way to do this as well?
Thanks in advance!
Function midString find the substring that is between two other strings "start" and "finish". If such a string does not exist, it returns "". A test code is included too.
void setup() {
test();
}
void loop() {
delay(100);
}
String midString(String str, String start, String finish){
int locStart = str.indexOf(start);
if (locStart==-1) return "";
locStart += start.length();
int locFinish = str.indexOf(finish, locStart);
if (locFinish==-1) return "";
return str.substring(locStart, locFinish);
}
void test(){
Serial.begin(115200);
String str = "Get a substring of a String. The starting index is inclusive (the corresponding character is included in the substring), but the optional ending index is exclusive";
Serial.print(">");
Serial.print( midString( str, "substring", "String" ) );
Serial.println("<");
Serial.print(">");
Serial.print( midString( str, "substring", "." ) );
Serial.println("<");
Serial.print(">");
Serial.print( midString( str, "corresponding", "inclusive" ) );
Serial.println("<");
Serial.print(">");
Serial.print( midString( str, "object", "inclusive" ) );
Serial.println("<");
}
just searched for this and saw no answer so i cooked one up.
i prefer working with String as well because of code readability and simplicity.
for me its more important than squeezing every last drop of juice out of my arduino.
String name = GetStringBetweenStrings("Hello, my name is John Doe# and my favourite number is 32#." ,"name is ","#");
String GetStringBetweenStrings(String input, String firstdel, String enddel){
int posfrom = input.indexOf(firstdel) + firstdel.length();
int posto = input.indexOf(enddel);
return input.substring(posfrom, posto);
}
watch out for the first case its fine, but for the second one you would have to change the second filter sting to "#." so it doesn't use the first occurrence of the #

C# check to see if an input contains only lowercase letters a-z

I'm stuck on a task of trying to print words that contain only lowercase letters a-z. I have already stripped out an inputted string if it contains any number 0-9 and if it contains an Uppercase letter:
String[] textParts;
textParts = text.Split(delimChars);
for (int i = 0; i < textParts.Length; i++) //adds s to words list and checks for capitals
{
String s = textParts[i];
bool valid = true;
foreach (char c in textParts[i])
{
if (char.IsUpper(c))
{
valid = false;
break;
}
if (c >= '0' && c <= '9')
{
valid = false;
break;
}
if (char.IsPunctuation(c))
{
valid = false;
break;
}
}
if (valid) pageIn.words.Add(s);
This is my code so far. The last part I'm trying to check to see if a word contains any punctuation (it's not working) is there an easier way I could do this and how could I get the last part of my code to work?
P.S. I'm not that comfortable with using Regex.
Many Thanks,
Ellie
Without regex, you can use LINQ (might be less performant)
bool isOnlyLower = s.Count(c => Char.IsLower(c)) == s.Length;
Count will retrieve the number of char that are in lower in the following string. If it match the string's length, string is composed only of lowercase letters.
An alternative would be to check if there's any UpperCase :
bool isOnlyLower = !s.Any(c => Char.IsUpper(c));
var regex = new Regex("^[a-z]+$");
if (!regex.IsMatch(input))
{
// is't not only lower case letters, remove input
}
I'm not sure whether I get your question right, but shouldn't the following work?
for (int i = 0; i < textParts.Length; i++) //adds s to words list and checks for capitals
{
String s = textParts[i];
if(s.Equals(s.ToLower()))
{
// string is all lower
}
}

C++/CLI - Split a string with a unknown number of spaces as separator?

I'm wondering how (and in which way it's best to do it) to split a string with a unknown number of spaces as separator in C++/CLI?
Edit: The problem is that the space number is unknown, so when I try to use the split method like this:
String^ line;
StreamReader^ SCR = gcnew StreamReader("input.txt");
while ((line = SCR->ReadLine()) != nullptr && line != nullptr)
{
if (line->IndexOf(' ') != -1)
for each (String^ SCS in line->Split(nullptr, 2))
{
//Load the lines...
}
}
And this is a example how Input.txt look:
ThisISSomeTxt<space><space><space><tab>PartNumberTwo<space>PartNumber3
When I then try to run the program the first line that is loaded is "ThisISSomeTxt" the second line that is loaded is "" (nothing), the third line that is loaded is also "" (nothing), the fourth line is also "" nothing, the fifth line that is loaded is " PartNumberTwo" and the sixth line is PartNumber3.
I only want ThisISSomeTxt and PartNumberTwo to be loaded :? How can I do this?
Why not just using System::String::Split(..)?
The following code example taken from http://msdn.microsoft.com/en-us/library/b873y76a(v=vs.80).aspx#Y0 , demonstrates how you can tokenize a string with the Split method.
using namespace System;
using namespace System::Collections;
int main()
{
String^ words = "this is a list of words, with: a bit of punctuation.";
array<Char>^chars = {' ',',','->',':'};
array<String^>^split = words->Split( chars );
IEnumerator^ myEnum = split->GetEnumerator();
while ( myEnum->MoveNext() )
{
String^ s = safe_cast<String^>(myEnum->Current);
if ( !s->Trim()->Equals( "" ) )
Console::WriteLine( s );
}
}
I think you can do what you need to do with the String.Split method.
First, I think you're expecting the 'count' parameter to work differently: You're passing in 2, and expecting the first and second results to be returned, and the third result to be thrown out. What it actually return is the first result, and the second & third results concatenated into one string. If all you want is ThisISSomeTxt and PartNumberTwo, you'll want to manually throw away results after the first 2.
As far as I can tell, you don't want any whitespace included in your return strings. If that's the case, I think this is what you want:
String^ line = "ThisISSomeTxt \tPartNumberTwo PartNumber3";
array<String^>^ split = line->Split((array<String^>^)nullptr, StringSplitOptions::RemoveEmptyEntries);
for(int i = 0; i < split->Length && i < 2; i++)
{
Debug::WriteLine("{0}: '{1}'", i, split[i]);
}
Results:
0: 'ThisISSomeTxt'
1: 'PartNumberTwo'

Resources