recheck outer if boolean true or false within it's else - if-statement

My goal is to recheck variable coolFeature boolean value from it's else
if (coolFeature) { // want to run this again after value becomes true in else below
$("#Editor").data("kendoWindow").width = '600';
$("#Editor").data("kendoWindow").title("Format Feature - " + Type + ' #' + graphic.attributes.OBJECTID);
$('#ndt').hide();
} else {
$("#Editor").data("kendoWindow").title("Edit Attributes - " + Type + ' #' + graphic.attributes.OBJECTID);
$('#ndt').show();
$("#ndt").click(function() {
$(this).data('clicked', true);
$("#Editor").data("kendoWindow").hide();
coolFeature = "true"; // want to reset to True here, then run the actions under initial if
});
}

I think you need simple recursion, I can't see the entire code so I can't tell exactly.
var myFunction = function(coolFeature) {
if(coolFeature) {
console.log("Cool");
} else {
myFunction(true);
}
};
myFunction(false);

Related

Flutter/Dart: How to return a List from a method and set it to another List

Problem: How to retrieve from a list and append to a new list saved locally, to be used by methods in the same class.
I would like to store whats in exerciseList and put it into the local variable
List CustomExercises; When I return custom exercises from getAllExercisesAsStrings() it doesn't update.
class GenerateCustom extends ExerciseListState {
int rnd;
GenerateCustom({this.difficulty});
final int difficulty;
String workout;
String ex1;
String ex2;
String ex3;
String ex4;
String ex5;
List customExercises = [];
//get list of custom workouts
List getAllExercisesAsStrings(customExercises) {
var n;
for (n = 0; n < exerciseList.length; n++) {
// print(exerciseList[n].title);
customExercises.add(exerciseList[n].title);
}
return customExercises;
}
For context the getCustomType() gets a random exercise from the list to be displayed.
String getCustomType() {
var random = Random();
var i = random.nextInt(customExercises.length);
print(customExercises[i]);
return customExercises[i];
}
String cExerciseOne() {
if (difficulty == 1) {
workout =
('1: ' + getCustomType() + ' ' + getRepsEasy() + 'x' + getSetsEasy());
} else if (difficulty == 2) {
workout = ('1: ' +
getCustomType() +
' ' +
getRepsMedium() +
'x' +
getSetsMedium());
} else {
workout =
('1: ' + getCustomType() + ' ' + getRepsHard() + 'x' + getSetsHard());
}
return workout;
}
When I print to console exerciseList[n].title it returns the list with the exercises e.g. ['exercise1','Bicep Curl', 'Pull Up', ] etc. These exercises have already been retrieved in the parent class and I would like to store them in the new list. Any guidance would be great and if you think more context is needed let me know.
The reason why List customExercises isn't populated is because customExercises.add() is being called inside a Stateful Widget. To add new Objects to the List, you'd need to call setState() when an item is added.
setState(() {
customExercises.add(exerciseList[n].title);
});

Validating the query parameter and parsing it using regular expression

I am new to regex, can you please tell me how to take a query parameter with all the below combinations.
(ParamName=Operator:ParamValue) is my set of query parameter value. This will be separated with ;(AND) or ,(OR) and i want to group them within braces. Like in below example
Ex: http://,host:port>/get?search=(date=gt:2020-02-06T00:00:00.000Z;(name=eq:Test,department=co:Prod))
Here the date should be greater than 2020-02-06 and name = Test or department contains Prod.
How to parse these query parameters. Please suggest.
Thanks, Vijay
So, I wrote a solution in JavaScript, but it should be adaptable in other languages as well, with a bit of research.
It's quite a bit of code, but what you're looking to achieve is not super easy!
So here's the code bellow, it's thoroughly commented, but please, if you there is something you don't understand, ask away, and I'll be happy to answer you :)
//
// The 2 first regexes are a parameter, which looks like date=gt:2020-02-06T00:00:00.000Z for example.
// The difference between those 2 is that the 1st one has **named capture group**
// For example '(?<operator>...)' is a capture group named 'operator'.
// This will come in handy in the code, to keep things clean
//
const RX_NAMED_PARAMETER = /(?:(?<param>\w+)=(?<operator>\w+):(?<value>[\w-:.]+))/
const parameter = "((\\w+)=(\\w+):([\\w-:.]+)|(true|false))"
//
// The 3rd parameter is an operation between 2 parameters
//
const RX_OPERATION = new RegExp(`\\((?<param1>${parameter})(?:(?<and_or>[,;])(?<param2>${parameter}))?\\)`, '');
// '---------.---------' '-------.------' '----------.---------'
// 1st parameter AND or OR 2nd parameter
my_data = {
date: new Date(2000, 01, 01),
name: 'Joey',
department: 'Production'
}
/**
* This function compates the 2 elements, and returns the bigger one.
* The elements might be dates, numbers, or anything that can be compared.
* The elements **need** to be of the same type
*/
function isGreaterThan(elem1, elem2) {
if (elem1 instanceof Date) {
const date = new Date(elem2).getTime();
if (isNaN(date))
throw new Error(`${elem2} - Not a valid date`);
return elem1.getTime() > date;
}
if (typeof elem1 === 'number') {
const num = Number(elem2);
if (isNaN(num))
throw new Error(`${elem2} - Not a number`);
return elem1 > num;
}
return elem1 > elem2;
}
/**
* Makes an operation as you defined them in your
* post, you might want to change that to suit your needs
*/
function operate(param, operator, value) {
if (!(param in my_data))
throw new Error(`${param} - Invalid parameter!`);
switch (operator) {
case 'eq':
return my_data[param] == value;
case 'co':
return my_data[param].includes(value);
case 'lt':
return isGreaterThan(my_data[param], value);
case 'gt':
return !isGreaterThan(my_data[param], value);
default:
throw new Error(`${operator} - Unsupported operation`);
}
}
/**
* This parses the URL, and returns a boolean
*/
function parseUri(uri) {
let finalResult;
// As long as there are operations (of the form <param1><; or ,><param2>) on the URL
while (RX_OPERATION.test(uri)) {
// We replace the 1st operation by the result of this operation ("true" or "false")
uri = uri.replace(RX_OPERATION, rawOperation => {
// As long as there are parameters in the operations (e.g. "name=eq:Bob")
while (RX_NAMED_PARAMETER.test(rawOperation)) {
// We replace the 1st parameter by its value ("true" or "false")
rawOperation = rawOperation.replace(RX_NAMED_PARAMETER, rawParameter => {
const res = RX_NAMED_PARAMETER.exec(rawParameter);
return '' + operate(
res.groups.param,
res.groups.operator,
res.groups.value,
);
// The "res.groups.xxx" syntax is allowed by the
// usage of capture groups. See the top of the file.
});
}
// At this point, the rawOperation should look like
// (true,false) or (false;false) for example
const res = RX_OPERATION.exec(rawOperation);
let operation;
if (res.groups.param2 === undefined)
operation = res.groups.param1; // In case this is an isolated operation
else
operation = res.groups.param1 + ({',': ' || ', ';': ' && '}[res.groups.and_or]) + res.groups.param2;
finalResult = eval(operation);
return '' + finalResult;
});
}
return finalResult;
}
let res;
res = parseUri("http://,host:port>/get?search=(date=gt:2020-02-06T00:00:00.000Z;(name=eq:Test,department=co:Prod))");
console.log(res);
res = parseUri("http://,host:port>/get?search=(date=lt:2020-02-06T00:00:00.000Z)");
console.log(res);

Regex to not allow space between words [duplicate]

I'm trying to write a regular expression to remove white spaces from just the beginning of the word, not after, and only a single space after the word.
Used RegExp:
var re = new RegExp(/^([a-zA-Z0-9]+\s?)*$/);
Test Exapmle:
1) test[space]ing - Should be allowed
2) testing - Should be allowed
3) [space]testing - Should not be allowed
4) testing[space] - Should be allowed but have to trim it
5) testing[space][space] - should be allowed but have to trim it
Only one space should be allowed. Is it possible?
To match, what you need, you can use
var re = /^([a-zA-Z0-9]+\s)*[a-zA-Z0-9]+$/;
Maybe you could shorten that a bit, but it matches _ as well
var re = /^(\w+\s)*\w+$/;
function validate(s) {
if (/^(\w+\s?)*\s*$/.test(s)) {
return s.replace(/\s+$/, '');
}
return 'NOT ALLOWED';
}
validate('test ing') // => 'test ing'
validate('testing') // => 'testing'
validate(' testing') // => 'NOT ALLOWED'
validate('testing ') // => 'testing'
validate('testing ') // => 'testing'
validate('test ing ') // => 'test ing'
BTW, new RegExp(..) is redundant if you use regular expression literal.
This one does not allow preceding and following spaces plus only one space between words. Feel free to add any special characters You want.
^([A-Za-z]+ )+[A-Za-z]+$|^[A-Za-z]+$
demo here
Working code- Inside my name.addTextChangedListener():
public void onTextChanged(CharSequence s, int start, int before, int count) {
String n = name.getText().toString();
if (n.equals(""))
name.setError("Name required");
else if (!n.matches("[\\p{Alpha}\\s]*\\b") | n.matches(".*\\s{2}.*") | n.matches("\\s.*")) {
if (n.matches("\\s.*"))
name.setError("Name cannot begin with a space");
else if (n.matches(".*\\s{2}.*"))
name.setError("Multiple spaces between texts");
else if (n.matches(".*\\s"))
name.setError("Blank space at the end of text");
else
name.setError("Non-alphabetic character entered");
}
}
You could try adapting this to your code.
var f=function(t){return Math.pow(t.split(' ').length,2)/t.trim().split(' ').length==2}
f("a a")
true
f("a a ")
false
f("a a")
false
f(" a a")
false
f("a a a")
false
Here is a solution without regular expression.
Add this script inside document.ready function it will work.
var i=0;
jQuery("input,textarea").on('keypress',function(e){
//alert();
if(jQuery(this).val().length < 1){
if(e.which == 32){
//alert(e.which);
return false;
}
}
else {
if(e.which == 32){
if(i != 0){
return false;
}
i++;
}
else{
i=0;
}
}
});
const handleChangeText = text => {
let lastLetter = text[text.length - 1];
let secondLastLetter = text[text.length - 2];
if (lastLetter === ' ' && secondLastLetter === ' ') {
return;
}
setInputText(text.trim());
};
use this
^([A-Za-z]{5,}|[\s]{1}[A-Za-z]{1,})*$
Demo:-https://regex101.com/r/3HP7hl/2

How to effectively use if and else for a filtering construct?

To parse function parameters I get from JavaScript, I need to perform a lot of checks. For example a function might expect an object as parameter that looks like this in JavaScript.
{
Fullscreen: [ 'bool', false ],
Size: [ 'Vector2u', 800, 600 ],
Title: [ 'string', 'Hello World' ],
// more properties...
}
In C++ I parse this by looping over all keys and check them. If one of those checks fail, an error message should be printed and this key value pair should be skipped. This is how my implementation looks at the moment. I hope you doesn't get distracted from some of the engine specific calls.
ModuleSettings *module = (ModuleSettings*)HelperScript::Unwrap(args.Data());
if(args.Length() < 1 || !args[0]->IsObject())
return v8::Undefined();
v8::Handle<v8::Object> object = args[0]->ToObject();
auto stg = module->Global->Get<Settings>("settings");
v8::Handle<v8::Array> keys = object->GetPropertyNames();
for(unsigned int i = 0; i < keys->Length(); ++i)
{
string key = *v8::String::Utf8Value(keys->Get(i));
if(!object->Get(v8::String::New(key.c_str()))->IsArray())
{
HelperDebug::Fail("script", "could not parse (" + key + ") setting");
continue;
}
v8::Handle<v8::Array> values = v8::Handle<v8::Array>::Cast(object->Get(v8::String::New(key.c_str())));
if(!values->Has(0) || !values->Get(0)->IsString())
{
HelperDebug::Fail("script", "could not parse (" + key + ") setting");
continue;
}
string type = *v8::String::Utf8Value(values->Get(0));
if(type == "bool")
{
if(!values->Has(1) || !values->Get(1)->IsBoolean())
{
HelperDebug::Fail("script", "could not parse (" + key + ") setting");
continue;
}
stg->Set<bool>(key, values->Get(1)->BooleanValue());
}
else if(type == "Vector2u")
{
if(!values->Has(1) || !values->Has(2) || !values->Get(1)->IsUint32(), !values->Get(2)->IsUint32())
{
HelperDebug::Fail("script", "could not parse (" + key + ") setting");
continue;
}
stg->Set<Vector2u>(key, Vector2u(values->Get(1)->Uint32Value(), values->Get(2)->Uint32Value()));
}
else if(type == "string")
{
if(!values->Has(1) || !values->Get(1)->IsString())
{
HelperDebug::Fail("script", "could not parse (" + key + ") setting");
continue;
}
stg->Set<string>(key, *v8::String::Utf8Value(values->Get(1)));
}
}
As you can see, I defined when happens when a check fails at every filter.
HelperDebug::Fail("script", "could not parse (" + key + ") setting");
continue;
I would like to only write that once, but I can only come up with a way using goto which I would like to prevent. Is there a better option to restructure the if else construct?
I think I'd start with a set of small classes to do the verification step for each type:
auto v_string = [](v8::Handle<v8::Array> const &v) {
return v->Has(1) && v->Get(1)->IsString();
}
auto v_Vector2u = [](v8::Handle<v8::Array> const &v) {
return v->Has(1) && v->Has(2) &&
v->Get(1)->IsUint32() && v->Get(2)->IsUint32();
}
// ...
Then I'd create a map from the name of a type to the verifier for that type:
std::map<std::string, decltyp(v_string)> verifiers;
verifiers["string"] = v_string;
verifiers["Vector2u"] = v_Vector2u;
// ...
Then to verify a type, you'd use something like this:
// find the verifier for this type:
auto verifier = verifiers.find(type);
// If we can't find a verifier, reject the data:
if (verifier == verifiers.end())
HelperDebug::Fail("script", "unknown type: " + type);
// found the verifier -- verify the data:
if (!verifier->second(values))
HelperDebug::Fail("script", "could not parse (" + key + ") setting");
A pretty usual way for such situations is to use a macro. That is #defined before or in the funciton and #undef-ed at function end. As you need continue there, the other ways are pretty much hosed.
goto would also be a solution but for this particular sample I'd not go with it.
A lighter way is to put at least the fail call into a function or lambda, what still leaves you with the continue part.
I'd probably make a macro that takes the filter expression as argument, leaving code like.
if(type == "bool")
{
ENSURE(values->Has(1) && values->Get(1)->IsBoolean());
stg->Set<bool>(key, values->Get(1)->BooleanValue());
}
...

Fuzzy Matches on dijit.form.ComboBox / dijit.form.FilteringSelect Subclass

I am trying to extend dijit.form.FilteringSelect with the requirement that all instances of it should match input regardless of where the characters are in the inputted text, and should also ignore whitespace and punctuation (mainly periods and dashes).
For example if an option is "J.P. Morgan" I would want to be able to select that option after typing "JP" or "P Morgan".
Now I know that the part about matching anywhere in the string can be accomplished by passing in queryExpr: "*${0}*" when creating the instance.
What I haven't figured out is how to make it ignore whitespace, periods, and dashes. I have an example of where I'm at here - http://jsfiddle.net/mNYw2/2/. Any help would be appreciated.
the thing to master in this case is the store fetch querystrings.. It will call a function in the attached store to pull out any matching items, so if you have a value entered in the autofilling inputfield, it will eventually end up similar to this in the code:
var query = { this.searchAttr: this.get("value") }; // this is not entirely accurate
this._fetchHandle = this.store.query(query, options);
this._fetchHandle.then( showResultsFunction );
So, when you define select, override the _setStoreAttr to make changes in the store query api
dojo.declare('CustomFilteringSelect', [FilteringSelect], {
constructor: function() {
//???
},
_setStoreAttr: function(store) {
this.inherited(arguments); // allow for comboboxmixin to modify it
// above line eventually calls this._set("store", store);
// so now, 'this' has 'store' set allready
// override here
this.store.query = function(query, options) {
// note that some (Memory) stores has no 'fetch' wrapper
};
}
});
EDIT: override queryEngine function as opposed to query function
Take a look at the file SimpleQueryEngine.js under dojo/store/util. This is essentially what filters the received Array items on the given String query from the FilteringSelect. Ok, it goes like this:
var MyEngine = function(query, options) {
// create our matching query function
switch(typeof query){
default:
throw new Error("Can not query with a " + typeof query);
case "object": case "undefined":
var queryObject = query;
query = function(object){
for(var key in queryObject){
var required = queryObject[key];
if(required && required.test){
if(!required.test(object[key])){
return false;
}
}else if(required != object[key]){
return false;
}
}
return true;
};
break;
case "string":
/// HERE is most likely where you can play with the reqexp matcher.
// named query
if(!this[query]){
throw new Error("No filter function " + query + " was found in store");
}
query = this[query];
// fall through
case "function":
// fall through
}
function execute(array){
// execute the whole query, first we filter
var results = arrayUtil.filter(array, query);
// next we sort
if(options && options.sort){
results.sort(function(a, b){
for(var sort, i=0; sort = options.sort[i]; i++){
var aValue = a[sort.attribute];
var bValue = b[sort.attribute];
if (aValue != bValue) {
return !!sort.descending == aValue > bValue ? -1 : 1;
}
}
return 0;
});
}
// now we paginate
if(options && (options.start || options.count)){
var total = results.length;
results = results.slice(options.start || 0, (options.start || 0) + (options.count || Infinity));
results.total = total;
}
return results;
}
execute.matches = query;
return execute;
};
new Store( { queryEngine: MyEngine });
when execute.matches is set on bottom of this function, what happens is, that the string gets called on each item. Each item has a property - Select.searchAttr - which is tested by RegExp like so: new RegExp(query).test(item[searchAttr]); or maybe a bit simpler to understand; item[searchAttr].matches(query);
I have no testing environment, but locate the inline comment above and start using console.debug..
Example:
Stpre.data = [
{ id:'WS', name: 'Will F. Smith' },
{ id:'RD', name:'Robert O. Dinero' },
{ id:'CP', name:'Cle O. Patra' }
];
Select.searchAttr = "name";
Select.value = "Robert Din"; // keyup->autocomplete->query
Select.query will become Select.queryExp.replace("${0]", Select.value), in your simple queryExp case, 'Robert Din'.. This will get fuzzy and it would be up to you to fill in the regular expression, here's something to start with
query = query.substr(1,query.length-2); // '*' be gone
var words = query.split(" ");
var exp = "";
dojo.forEach(words, function(word, idx) {
// check if last word
var nextWord = words[idx+1] ? words[idx+1] : null;
// postfix 'match-all-but-first-letter-of-nextWord'
exp += word + (nextWord ? "[^" + nextWord[0] + "]*" : "");
});
// exp should now be "Robert[^D]*Din";
// put back '*'
query = '*' + exp + '*';