how to get the deleted item value using javascript - javascript

I have removed an element from an array. Now, I need to display which item is deleted and the remaining items, but have been unsuccessful. Suppose, the array looks like:
let person = ['Cercei','Snow','Arya','Sansa']
I have removed 'Snow' and 'Cercei'. So, I need to display two things into two different new array.
delPerson = ['Cercei','Snow']
remArray = ['Arya','Sansa']
How can this be done with JavaScript? In my application, I have delete icon with each and every name so i can remove any name. I want to get the deleted name and remaining name into two different array. Please help me how to do that using javascript or lodash
let me tell you my application code:
let person = personData.map(n => n.name)
let remPerson = person.filter(p => person.indexOf(p) !== -1)
Now, person and remPerson array is showing same value. While comparing the length it is creating the problem.

One way could be to use Array.reduce.
const persons = ['Cercei', 'Snow', 'Arya', 'Sansa'];
const {
deleted,
kept
} = persons.reduce((acc, person) => {
// Note: The deletion condition may vary
if (person === 'Cercei' || person === 'Snow') {
acc.deleted.push(person);
} else {
acc.kept.push(person);
}
return acc;
}, {
deleted: [],
kept: []
});
console.log(deleted);
console.log(kept);

You can use splice, but this will modify your original array. It is unclear to me if that will be ok in the OP's case. Here's Mozilla's documentation on splice: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/splice
let person = ['Cercei','Snow','Arya','Sansa'];
let delPerson = person.splice(0, 2);
console.log(delPerson);
console.log(person);

You can remove items using splice and also keep track of two separate arrays:
let personData = [{name:'Cercei'},{name:'Snow'},{name:'Arya'},{name:'Sansa'}];
let person = personData.map(n=>n.name);
let removeItems = ['Cercei','Snow'];
let delPerson = [];
removeItems.forEach(item=>{
delPerson.push(
...person.splice( person.indexOf(item), 1 )
)
});
console.log('delPerson: ', delPerson);
console.log('remaining: ', person);

Related

React.JS Storing mapped API repsonse into a new array based on matching values

Using React, I have data from an API response. I mapped the data and am storing the visitID, which would be the main identifier, into a variable. What I would like to do is look for any matching visitID values and store them into a new array, the issue I'm having is each instance is being stored in it's own array, for example:
['7065682'] at Index 0
['7065682'] at Index 1
['7065682'] at Index 2
['7047674'] at Index 3
['7047674'] at Index 4
I would like to look through each iteration and check all, put matching values into it's own array so I can write some logic based off each unique value. I just don't understand how to look through the next iteration. Here's my code, and the function 'duplicateVisitID' that I've been trying, but it doesn't give me the results I'm looking for.
{
Object.keys(this.state.EncounterData).length !== 0 ?
Object.values(this.state.EncounterData).map((encounter, i) => {
const visitID = [encounter.resource.identifier[1].value];
console.log(visitID, i);
const duplicateVisitID = function (visitID) {
if (visitID[i] === visitID[i])
return [visitID.concat(visitID[i])]
}
I am not sure what do you want to do, but if I understood right you want new array with only strings that are unique, not repeating. If yes see the code below. This is not the best performing one because of iteration inside iteration, but it will work for you. You can optimize it later by applying some algorithms.
The newArr is equal to ['7065682', '7047674']
const EncounteredData = [['7065682'], ['7065682'], ['7065682'], ['7047674'], ['7047674']];
const newArr = [];
for(let i of EncounteredData) {
for(let j of EncounteredData) {
if((i[0] !== j[0]) && !newArr.includes(i[0])) newArr.push(i[0]);
}
}
console.log(newArr);
If I understand correctly, you want an array of unique values? If so then you can use the map function and add any unique values to an array if the value is not already in it:
const uniqueVals = [];
EncounteredData.map((visitID) => {
if (!uniqueVals.includes(visitID[0])) {
uniqueVals.push(visitID[0]);
}
});

Get a key in a JavaScript object by its value and rename it

I have a list of variables that I will form into an array with keys and values. However, before making them as array I want to check if any of their values matches a
specific string and change their keys names into something else.
Lets say this is the list of variables
customer1 = "Jack", customerDate1 = "08/13/2021", customer2 = "Michael", customerDate2 = "01/01/2021", customer3 = "Luna",customerDate3 = "03/10/2021";
The array before running condition check will be
data = [{key1:"Jack", keyDate1:"08/13/2021",key2:"Michael", keyDate2:"01/01/2021",key3:"Luna", keyDate3:"10" }];
Lets say the condition is:
customerName = "Jack";
I want the cross check customerName variable with the following variables (customer1,customer2,customer3) and if the condition meets any of them, then their keys in the array changes:
for example the condition meets customer1 then both keys of customer1 and customerDate1 changes to something else, to become something like
data = [{conditionMet1:"Jack", conditionDateMet1:"08/13/2021",key2:"Michael", keyDate2:"01/01/2021",key3:"Luna", keyDate3:"10" }];
I am appreciating any help or guidance.
A little bit tricky as alghoritm but it works:
let data = [{key1:"Jhon", keyDate1:"08/13/2021",key2:"Eric", keyDate2:"01/01/2021",key3:"Jack", keyDate3:"10" }];
let i = 1;
let result = [];
let explored = [];
data.forEach(x => {
let resultObj = {};
for (const [key, val] of Object.entries(x)) {
let newKey = key;
let newKeyDate = null;
if (val === "Jack") {
newKey = "conditionMet" + i;
newKeyDate = "conditionDateMet" + i;
}
if (!explored.includes(key)) resultObj[newKey] = val;
if (newKeyDate) {
resultObj[newKeyDate] = x["keyDate" + i];
explored.push("keyDate" + i)
}
if(!key.includes("Date")) i++;
}
result.push(resultObj)
})
console.log(result)
Basically for each element in data I explore all the entries and if I found condition I add conditionMet1 and conditionDateMet1 to object, otherwise what I found on object itself.
Perhaps not very elegant, but for the example given you could do something like this:
if(specialCondition){
data = [{specialKey1:customer1, specialDate1:customerDate1,key2:customer2...];
}else{
data = [{key1:customer1, keyDate1:customerDate1,key2:customer2...];
}
I don't think it is possible to rename a key but you can always create a new key by
object["newKeyName"] = object.previousKey
And optionally you can remove the old key by
delete object.previousKey
That way you will remove the previous key if you don't want it anymore.
Say you have 6 variables.
customer1, customerDate1, customer2, customerDate2, customer3,customerDate3;
You could make an array, by customer
const data = [{
id: customer1,
date: customerDate1
},{
id: customer2,
date: customerDate2
},{
id: customer3,
date: customerDate3
}];
This is now quite useful. Say you want to know which customer meets some condition. (for example id is "Jack"), using Array.find
const jack = data.find(item => item.id === "Jack");
console.log(jack);
Or to find which customers have a date before "now", using Array.filter
const now = Date.now();
const beforeNow = data.filter(item => item.date < now);
console.log(beforeNow);

Filtering duplicates form array of objects

looking for an explanation as to why the below code doesn't filter correctly. I have an array of objects, one of those properties is buy_mth_yr which is in the format mmm-yy as below.
buy_mth_yr : 'Apr-18'
I am trying to get a list of all unique buy_mth_yr values and return as a list of label-value objects, to be passed into a filter. I have already found a solution in a separate stack overflow question, the point of me asking this question is more to understand why my original solution below doesn't work. so lets say data is my list of objects with the buy_mth_yr key. the if statement calls every time and I end up with an unfiltered list. any help/insight appreciated!
let distinct = [];
data.forEach(record =>{
let temp = {label: record.buy_mth_yr, value: record.buy_mth_yr}
if(!(temp in distinct)){
distinct.push(temp)
}
})
return distinct;
to understand why my original solution below doesn't work
Because you are doing a referential comparison - first link that popped up on google, it might help: https://dmitripavlutin.com/how-to-compare-objects-in-javascript/#1-referential-equality
({a:1}) !== ({a:1})
// but
const obj = {a:1};
obj === obj
temp will never be in distinct because it is always a new object, every time.
EDIT:
To add to this, a better solution (and there's a thousand ways to write this, below is but one example) would look like this:
const isShallowEqualWith = (a) => (b) => {
const keysA = Object.keys(a);
const keysB = Object.keys(b);
return keysA.length === keysB.length && keysA.every(k => a[k] === b[k]);
}
let distinct = [];
data.forEach(record =>{
let temp = {label: record.buy_mth_yr, value: record.buy_mth_yr}
if(!distinct.find(isShallowEqualWith(temp)) {
distinct.push(temp);
}
})
return distinct;
I think your !(temp in distinct) is not the check you want to do : use !distinct.includes(temp) instead.
However you should take a look to lodash library with _.uniq and _.uniqBy functions : https://www.geeksforgeeks.org/lodash-_-uniqby-method/

Remove Strings From Array

I'm trying to make an array of objects from the browsing history that can become links in a React list.
What this does is takes the history element and pushes it to the user object, then I take the name and ID, and splice it back into the array. I then filter it down to distinct values.
What I am left with, is an array that looks like this:
[{id1,name1},{id2,name2},{id3,name3},"id1","id2","id3"]
which is almost exactly what I want, except if I'm going to map that to create links, I need to get rid of the string values.
It occurred to me to try skipping the history element and just make an array of matches, and any number of other things.
pop and shift don't work to isolate the first object because then the whole function continually returns a single item.
This is the only way I have gotten a result close to what I want, I just need a simple way of filtering out string values from an array after it's created, or maybe before it's mapped out.
const getLead = async _id => {
const res = await axios.get(`/api/leads/${_id}`);
dispatch({
type: GET_LEAD,
payload: res.data
});
const { name } = res.data
const match = { name, _id }
const setPrevious = () => {
const prevLeads = user.prevLeads
const history = createBrowserHistory(getLead);
const prevLead = history.location.pathname.slice(6);
prevLeads.push(prevLead);
return prevLeads;
}
const prevLeads = setPrevious();
const [...spliceLeads] = prevLeads.splice(0,1,match,match);
const distinct = (value, index, self) => {
return self.indexOf(value) === index;
}
const recentLeads = prevLeads.filter(distinct) ;
console.log(spliceLeads)
}
You just check the type in your .filter logic:
const array = [
{ test: 'ing' },
1,
new Date(),
'this should be removed'
];
const result = array.filter(e => typeof e !== 'string');
console.log(result);
The solution what has been provided already works like charm, that should be used for your solution, below I'm providing a bit different way to figure out if the element is a string or not.
I guess filter() is a good way to test each elements on an array and return only the passing once as a result. If you call on each item Object.prototype.toString.call(e) then it will return as a text if you have [object String] or something else. This can be also used to filter out your string values from your array.
See the example below:
const prevLeads = [{id:'id1',name: 'name1'},{id: 'id2',name:'name2'},{id:'id3',name:'name3'},"id1","id2","id3"];
const filter = e => Object.prototype.toString.call(e) !== '[object String]';
const recentLeads = prevLeads.filter(filter);
console.log(recentLeads);
I hope that helps!

filter an array of objects based on key/value and remove it from array

In the following function I push and object to the accountsToDelete array, I need to then remove the matching object from the accountsToAdd array. I am guessing I would have to use a combination of IndexOf, Filter, Reduce but I am still a little rough in understanding how to accomplish this. This is the current function:
accountDelete(id, name) {
const accountsToAdd = this.userForm.value.accountsToAdd;
const accountsToDelete = this.userForm.value.accountsToDelete;
this.userForm.value.accountsToDelete.push(
{
id: id,
name: name
}
);
}
You can simply use the filter function. By this you can say, that in the accountToAdd all entries should be filtered, which id fits the to deleted account.
An example:
// Initialize both lists.
let accountsToAdd = []
let accountsToDelete = []
// Preparation by adding a account to the first list.
const account = { id: 1, name: 'Max' }
accountsToAdd.push(account)
// Mark account to be removed.
accountsToDelete.push(account)
accountsToAdd = accountsToAdd.filter(acc => acc.id !== account.id)
// Verify result.
console.log(accountsToAdd)
console.log(accountsToDelete)
Note:
Your both lists are defined as constant. By this you can't use the reassignment.

Categories

Resources