0

I need to filter an JS object as below format. I have some array of Object. every object contain title and data. I need to filter the object. title will not repet in object it will make an array of data and store every data in that. Object

 let results = [
            {
                "title": "exam",
                "data": {
                    "status": "Active",
                    "studentId": "44",
                    "universityId": "0",
                    "mediaId": "12",
                    "mediaName": "massey university",
                    "mediaSrc": "https://unisearch-static-contents.s3.ap-southeast-1.amazonaws.com/ADMIN/massey%20university-9a2b9a22-b648-4ef1-a806-97bb0da9b337.jpg",
                    "mediaDownload": 4
                }
            },
            {
                "title": "prospectus",
                "data": {
                    "status": "Active",
                    "studentId": "44",
                    "universityId": "0",
                    "mediaId": "12",
                    "mediaName": "massey university",
                    "mediaSrc": "https://unisearch-static-contents.s3.ap-southeast-1.amazonaws.com/ADMIN/massey%20university-9a2b9a22-b648-4ef1-a806-97bb0da9b337.jpg",
                    "mediaDownload": 4
                }
            },
            {
                "title": "prospectus",
                "data": {
                    "status": "Active",
                    "studentId": "44",
                    "universityId": "23",
                    "mediaId": "12",
                    "mediaName": "massey university",
                    "mediaSrc": "https://unisearch-static-contents.s3.ap-southeast-1.amazonaws.com/ADMIN/massey%20university-9a2b9a22-b648-4ef1-a806-97bb0da9b337.jpg",
                    "mediaDownload": 4
                }
            },]

Filter object will be like this. title will not be repeated it will make an array.

 "results": [
            {
                "title": "exam",
                "data": {
                    "status": "Active",
                    "studentId": "44",
                    "universityId": "0",
                    "mediaId": "12",
                    "mediaName": "massey university",
                    "mediaSrc": "https://unisearch-static-contents.s3.ap-southeast-1.amazonaws.com/ADMIN/massey%20university-9a2b9a22-b648-4ef1-a806-97bb0da9b337.jpg",
                    "mediaDownload": 4
                }
            },
            {
                "title": "prospectus",
                "data": [{
                    "status": "Active",
                    "studentId": "44",
                    "universityId": "0",
                    "mediaId": "12",
                    "mediaName": "massey university",
                    "mediaSrc": "https://unisearch-static-contents.s3.ap-southeast-1.amazonaws.com/ADMIN/massey%20university-9a2b9a22-b648-4ef1-a806-97bb0da9b337.jpg",
                    "mediaDownload": 4
                },
                {
                    "status": "Active",
                    "studentId": "44",
                    "universityId": "23",
                    "mediaId": "12",
                    "mediaName": "massey university",
                    "mediaSrc": "https://unisearch-static-contents.s3.ap-southeast-1.amazonaws.com/ADMIN/massey%20university-9a2b9a22-b648-4ef1-a806-97bb0da9b337.jpg",
                    "mediaDownload": 4
                }]

I have tried this.

let filterData = [];
mainData.data.results.map((value) => {
  if (filterData.length == 0) {
    let obj = {
      title: "title",
      data: [{ ...value.data }],
    };
    filterData.push(obj);
  } else {
    let found = false;
  }
});
4
  • construct of data property is not sync Commented May 12, 2022 at 4:24
  • if it's unique data, you prefer to display it as an object instead of an array? That object is not consistent with your multiple similar data in an array Commented May 12, 2022 at 4:27
  • Are you sure you want the resulting data to be either an object or an array? I would recommend using an array for all of them, even if for only one entry just so you've got a consistent API Commented May 12, 2022 at 4:27
  • I need an new array like this. Commented May 12, 2022 at 4:34

3 Answers 3

1

This isn't really a filter operation, more of a reduce job where you want to collect data for the same title.

For that, I'd recommend creating a map of title to data

// this is just your data structure minified
const results = [{"title":"exam","data":{"status":"Active","studentId":"44","universityId":"0","mediaId":"12","mediaName":"massey university","mediaSrc":"https://unisearch-static-contents.s3.ap-southeast-1.amazonaws.com/ADMIN/massey%20university-9a2b9a22-b648-4ef1-a806-97bb0da9b337.jpg","mediaDownload":4}},{"title":"prospectus","data":{"status":"Active","studentId":"44","universityId":"0","mediaId":"12","mediaName":"massey university","mediaSrc":"https://unisearch-static-contents.s3.ap-southeast-1.amazonaws.com/ADMIN/massey%20university-9a2b9a22-b648-4ef1-a806-97bb0da9b337.jpg","mediaDownload":4}},{"title":"prospectus","data":{"status":"Active","studentId":"44","universityId":"23","mediaId":"12","mediaName":"massey university","mediaSrc":"https://unisearch-static-contents.s3.ap-southeast-1.amazonaws.com/ADMIN/massey%20university-9a2b9a22-b648-4ef1-a806-97bb0da9b337.jpg","mediaDownload":4}}];

// Collect data by title
const collect = results.reduce(
  (map, { title, data }) => ({
    ...map,
    [title]: [...(map[title] ?? []), data],
  }),
  {}
);

// Convert the mapped object to an array of objects
// with `title` and `data` properties
const filterData = Object.entries(collect).map(([title, data]) => ({
  title,
  data,
}));

console.log(filterData);
.as-console-wrapper { max-height: 100% !important; }

This will always put data in an array which keeps your data-structure consistent. If you really want single-element arrays to be destructured, use this instead for the last part

const filterData = Object.entries(collect).map(([title, data]) => ({
  title,
  data: data.length === 1 ? data[0] : data,
}));
Sign up to request clarification or add additional context in comments.

4 Comments

please see the question again I have updated that. and collect is not defined throwing an error
@Md.GolamRabbani updated what? You can clearly see from the snippet in my answer that there is no error thrown
SyntaxError: Unexpected token ? [title]: [...(map[title] ?? []), data],
@Md.GolamRabbani how are you running this code? The nullish coalescing operator (??) is available in everything except Internet Explorer
0

The main problem here is to remember which title already exists and reduce it to just one with the data of all the same titles.

The above solution is good but it has a complexity of O(n^2) because it performs two loops. One to reduce the elements into an array of { title: [datas]} objects and one to transform it into the desired output of the form [{title, datas},...].

Using this solution we can perform the process with a complexity of O(n), using a hash table (directory) structure to remember the titles and reduce only those that are repeated.

let filterData = []
let directory = {}
mainData.data.results.map( (obj) => {
     if(directory[obj.title] === undefined) {
     directory[obj.title] = filterData.length
     filterData.push({title: obj.title, data: [obj.data] })
   } else {
     filterData[directory[obj.title]].data.push(obj.data)
   }
})

Comments

0
var resultObj = {}

results.forEach((item)=>{
    if(!resultObj[item.title]){
        resultObj[item.title] = {
            title:item.title,
            data:[]
        }
    }
    resultObj[item.title].data.push(item.data)
})

var finalResultList = Object.values(resultObj)

console.log(finalResultList)

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.