Find a value within array of structures - coldfusion

this might have been asked before, but didn't quite find... or what I found was old.
I have an array of structures like so:
Isn't there a CFML function that will allow me to check if "test#email.com" already exists under any of the structures "toAddress" ? I can obviously loop my array, check and break if found, but wondering if something already exists for this ?
Thank you.
Pat

You can use arrayFind() with a callback function. Using your data structure above and assume the array is named myArray
if(
!arrayFind( myArray, function( item ){
return item.toAddress == 'test#email.com'
})
){
// do stuff if address is not used.
}

Related

Declaring a std::list with an array index C++

I was following a hash table implementation online (https://www.youtube.com/watch?v=2_3fR-k-LzI) when I observed the video author initialize a std::list with an array index. This was very confusing to me as I was always under the impression that std::list was always meant to operate like a linked list and was not capable of supporting random indexing. However, I thought it was maybe a weird way to declare the size of a list and ignored it and moved on. Specifically, he did the following:
static const int hashGroups = 10;
std::list<std::pair<int, std::string>> table[hashGroups];
Upon trying to implement a function to search to see if a key resided in the hash table, I realized that I could not access the std::list objects as I would expect to be able to. In HashTable.cpp (which includes the header file that defines the two variables above) I was only able to access the table member variable's elements as a pointer with -> instead of with . as I would expect to be able to. It looks like what is directly causing this is using the array index in the list definition. This seems to change the type of the table variable from a std::list to a pointer to a std::list. I do not understand why this is the case. This also appears to break my current implementation of attempting to iterate through the table variable because when I declare an iterator to iterate through table's elements, I am able to see that the table has the correct data in the VS debugger but the iterator seems to have completely invalid data and does not iterate through the loop even once despite seeing table correctly have 10 elements. My attempt at the search function is pasted below:
std::string HashTable::searchTable(int key) {
for (std::list<std::pair<int, std::string>>::const_iterator it = table->begin(); it != table->end(); it++)
{
if (key == it->first) {
return it->second;
}
std::cout << "One iteration performed." << std::endl;
}
return "No value found for that key.";
}
With all of this being said, I have several burning questions:
Why are we even able to declare a list with brackets when a std::list does not support random access?
Why does declaring a list like this change the type of the list from std::list to a pointer?
What would be the correct way to iterate through table in its current implementation with an iterator?
Thank you for any help or insight provided!
After reading the responses from #IgorTandetnik I realized that I was thinking about the list incorrectly. What I didn't fully understand was that we were declaring an array of lists and not attempting to initialize a list like an array. Once I realized this, I was able to access the elements correctly since I was not trying to iterate through an array with an iterator for a list. My revised searchTable function which to my knowledge now works correctly looks like this:
std::string HashTable::searchTable(int key) {
int hashedKey = hashFunction(key);
if (table[hashedKey].size() > 0)
{
for (std::list<std::pair<int, std::string>>::const_iterator it = table[hashedKey].begin(); it != table[hashedKey].end(); it++)
{
if (key == it->first) {
return it->second;
}
}
}
return "No value found for that key.";
}
And to answer my three previous questions...
1. Why are we even able to declare a list with brackets when a std::list does not support random access?
Response: We are declaring an array of std::list that contains a std::pair of int and std::string, not a list with the array index operator.
2. Why does declaring a list like this change the type of the list from std::list to a pointer?
Response: Because we are declaring table to be an array (which is equivalent to a const pointer to the first element) which contains instances of std::list. So we are never "changing" the type of the list variable.
3. What would be the correct way to iterate through table in its current implementation with an iterator?
Response: The current implementation only attempts to iterate over the first element of table. Create an iterator which uses the hashed key value as the array index of table and then tries to iterate through the std::list that holds instances of std::pair at that index.

concurrent_vector invalid data

using : VC++ 2013
concurrency::concurrent_vector<datanode*> dtnodelst
Occasionally when I do dtnodelst->at(i) .... I am getting an invalid address (0XCDCD.. ofc)
which shouldn't be the case cause after I do push back, I never delete or remove any of the itms ( even if I delete it should have returned the deleted old address... but I am not ever deleting so that is not even the case )
dtnodelst itm = new dtnodelst ();
....
dtnodelst->push_back(itm);
any ideas on what might be happening ?
p.s. I am using windows thread pool. some times .. I can do 8million inserts and find and everything goes fine .... but sometimes even 200 inserts and finds will fail. I am kind of lost. any help would be awesomely appreciated!!
thanks and best regards
actual code as an fyi
p.s. am I missing something or is it pain in the ass to past code with proper formatting ? I remember it being auto align before ... -_-
struct datanode {
volatile int nodeval;
T val;
};
concurrency::concurrent_vector<datanode*> lst
inline T find(UINT32 key)
{
for (int i = 0; i < lst->size(); i++)
{
datanode* nd = lst->at(i);
//nd is invalid sometimes
if (nd)
if (nd->nodeval == key)
{
return (nd->val);
}
}
return NULL;
}
inline T insert_nonunique(UINT32 key, T val){
datanode* itm = new datanode();
itm->val = val;
itm->nodeval = key;
lst->push_back(itm);
_updated(lst);
return val;
}
The problem is using of concurrent_vector::size() which is not fully thread-safe as you can get reference to not yet constructed elements (where memory contains garbage). Microsoft PPL library (which provides it in concurrency:: namespace) uses Intel TBB implementation of concurrent_vector and TBB Reference says:
size_type size() const |
Returns: Number of elements in the vector. The result may include elements that are allocated but still under construction by concurrent calls to any of the growth methods.
Please see my blog for more explanation and possible solutions.
In TBB, the most reasonable solution is to use tbb::zero_allocator as underlying allocator of concurrent_vector in order to fill newly allocated memory with zeroes before size() will count it too.
concurrent_vector<datanode*, tbb::zero_allocator<datanode*> > lst;
Then, the condition if (nd) will filter out not-yet-ready elements.
volatile is no substitute for atomic<T>. Do not use volatile in some attempt to provide synchronization.
The whole idea of your find call doesn't make sense in a concurrent context. As soon as the function iterates over one value, it could be mutated by another thread to be the value you're looking for. Or it could be the value you want, but mutated to be some other value. Or as soon as it returns false, the value you're seeking is added. The return value of such a function would be totally meaningless. size() has all the same problems, which is a good part of why your implementation would never work.
Inspecting the state of concurrent data structures is a very bad idea, because the information becomes invalid the moment you have it. You should design operations that do not require knowing the state of the structure to execute correctly, or, block all mutations whilst you operate.

Remove element from vector error C++

I know this might seem as a duplicate question, but it is not, I have a problem with a function and don''t know why it behaves like that.
I have a vector which holds elements of type MyMaterial** (std::vector). At a point in my program, I will know an element, "currentElement", and I will want to remove it.
I tried doing this:
myMaterials.erase(currentElement);
But here is the problem: Instead of only deleting "currentElement", it also deletes all elements added after it. Why does it do that and how can I solve it?
I must mention that I don''t know the position of "currentElement" in the vector, and i prefere not to search for it, I''m hoping there is another way.
If you are using std::vector, then:
Erase elements Removes from the vector either a single element
(position) or a range of elements ([first,last)).
Maybe you are looking for something like this:
How do I remove an item from a stl vector with a certain value?
To use vector::erase(iterator) to remove an element from a vector, you may either have to know its index OR iterate thru the list to hunt for it.
Luckily, There is the std::map, and this is how you would work it
std::map<std::string,myMaterial> myMaterials;
myMaterial mat;//assuming it doesnt take any args
myMaterials['myMaterialXYZ'] = mat; ///add it to the array
myMaterials.erase('myMaterialXYZ'); ///Erase by key..(or "name" in this case)
Now you can easily track string names instead of ever changing index positions...and memory locations, which by the way may be another ace up your sleeve.
I couldn''t really use the examples given by you above, because I got all kinds of errors, due to the type of elements the vector holds. But I made a function which managed to delete the specific element:
int i=0;
int found=0;
MyMaterial **material = gMaterials.begin();
while(material != gMaterials.end() && found == 0)
{
if(currentElement == material)
{
gMaterials.erase(gMaterials.begin() + i, gMaterials.begin() + i+1);
found = 1;
}
i++;
cloth++;
}
I don''t know how good/correct it is, but it does the job.
Thank you very much for the suggestions and the help.

C++ newbie: writing a function for extracting i vectors from a file. How do I get i/unkown number of vectors out of the function?

I am writing a function for getting datasets from a file and putting them into vectors. The datasets are then used in a calculation. In the file, a user writes each dataset on a line under a heading like 'Dataset1'. The result is i vectors by the time the function finishes executing. The function works just fine.
The problem is that I don't know how to get the vectors out of the function! (1) I think I can only return one entity from a function. So I can't return i vectors. Also, (2) I can't write the vectors/datasets as function parameters and return them by reference because the number of vectors/datasets is different for each calculation. If there are other possibilities, I am unaware of them.
I'm sure this is a silly question, but am I missing something here? I would be very grateful for any suggestions. Until now, I have not put the vector/dataset extraction code into a function; I have kept it in my main file, where it has worked fine. I would now like to clean up my code by putting all data extraction code into its own function.
For each calculation, I DO know the number of vectors/datasets that the function will find in the file because I have that information written in the file and can extract it. Is there some way I could use this information?
If each vector is of the same type you can return a
std::vector<std::vector<datatype> >
This would look like:
std::vector<std::vector<datatype> > function(arguments) {
std::vector<std::vector<datatype> > return_vector;
for(int i =0; i < rows; ++i) {
\\ do processing
return_vector.push_back(resulting_vector);
}
return return_vector;
}
As has been mentionned, you may simply use a vector of vectors.
In addition, you may want to add a smart pointer around it, just to make sure you're not copying the contents of your vectors (but that's already an improvement. First aim at something that works).
As for the information on the number of vectors, you may use it by resizing the global vector to the appropriate value.
You question is, at its essence "How do I return a pile of things from a function?" It happens that your things are vector<double>, but that's not really important. What is important is that you have a pile of them of unknown size.
You can refine your thinking by rephrasing your one question into two:
How do I represent a pile of things?
How do I return that representation from a function?
As to the first question, this is precisely what containers do. Containers, as you surely know because you are already using one, hold an arbitrary numbers of similar objects. Examples include std::vector<T> and std::list<T>, among others. Your choice of which container to use is dictated by circumstances you haven't mentioned -- for example, how expensive are the items to copy, do you need to delete an item from middle of the pile, etc.
In your specific case, knowing what little we know, it seems you should use std::vector<>. As you know, the template parameter is the type of the thing you want to store. In your case that happens to be (coincidentally), an std::vector<double>. (The fact that the container and its contained object happen to be similar types is of no consequence. If you need a pile of Blobs or Widgets, you say std::vector<Blob> or std::vector<Widget>. Since you need a pile of vector<double>s, you say vector<vector<double> >.) So you would declare it thus:
std::vector<std::vector<double > > myPile;
(Notice the space between > and >. That space is required in the previous C++ standard.)
You build up that vector just as you did your vector<double> -- either using generic algorithms, or invoking push_back, or some other way. So, your code would look like this:
void function( /* args */ ) {
std::vector<std::vector<double> > myPile;
while( /* some condition */ ) {
std::vector<double> oneLineOfData;
/* code to read in one vector */
myPile.push_back(oneLineOfData);
}
}
In this manner, you collect all of the incoming data into one structure, myPile.
As to the second question, how to return the data. Well, that's simple -- use a return statement.
std::vector<std::vector<double> > function( /* args */ ) {
std::vector<std::vector<double> > myPile;
/* All of the useful code goes here*/
return myPile;
}
Of course, you could also return the information via a passed-in reference to your vector:
void function( /* args */, std::vector<std::vector<double> >& myPile)
{
/* code goes here. including: */
myPile.push_back(oneLineOfData);
}
Or via a passed-in pointer to your vector:
void function( /* args */, std::vector<std::vector<double> >* myPile)
{
/* code goes here. */
myPile->push_back(oneLineOfData);
}
In both of those cases, the caller must create the vector-of-vector-of-double before invoking your function. Prefer the first (return) way, but if your program design dictates, you can use the other ways.

Simplest lua function that returns a vector of strings

I need a very simple c++ function that calls a lua function that returns an array of strings, and stores them as a c++ vector. The function can look something like this:
std::vector<string> call_lua_func(string lua_source_code);
(where lua source code contains a lua function that returns an array of strings).
Any ideas?
Thanks!
Here is some source that may work for you. It may need some more polish and testing. It expects that the Lua chunk is returning the array of strings, but with slight modification could call a named function in the chunk. So, as-is, it works with "return {'a'}" as a parameter, but not "function a() return {'a'} end" as a parameter.
extern "C" {
#include "../src/lua.h"
#include "../src/lauxlib.h"
}
std::vector<string> call_lua_func(string lua_source_code)
{
std::vector<string> list_strings;
// create a Lua state
lua_State *L = luaL_newstate();
lua_settop(L,0);
// execute the string chunk
luaL_dostring(L, lua_source_code.c_str());
// if only one return value, and value is a table
if(lua_gettop(L) == 1 && lua_istable(L, 1))
{
// for each entry in the table
int len = lua_objlen(L, 1);
for(int i=1;i <= len; i++)
{
// get the entry to stack
lua_pushinteger(L, i);
lua_gettable(L, 1);
// get table entry as string
const char *s = lua_tostring(L, -1);
if(s)
{
// push the value to the vector
list_strings.push_back(s);
}
// remove entry from stack
lua_pop(L,1);
}
}
// destroy the Lua state
lua_close(L);
return list_strings;
}
First of all, remember Lua arrays can contain not only integers but also other types as keys.
Then, you can import the Lua source code using luaL_loadstring.
At this point, the only requirement left is the "return vector".
Now, you can use lua_istable to check whether a value is a table(array) and use lua_gettable to extract the multiple fields(see http://www.lua.org/pil/25.1.html) and manually add them one by one to the vector.
If you can not figure out how to deal with the stack, there seem to be some tutorials to help you. To find the number of elements, I found this mailing list post, which might be helpful.
Right now, I don't have Lua installed, so I can't test this information. But I hope it helps anyway.
Not really an answer to your question:
I've had a lot of trouble when writing c++ <=> lua interface code with the plain lua c-api. Then I tested many different lua-wrapper and I really suggest luabind if you are trying to achieve anything more or less complex. It's possible to make types available to lua in seconds, the support for smart pointers works great and (compared to other projects) the documentation is more or less good.