'Filter custom object array based on another array of type int in f#

I have two arrays in f# 1st Array is called CompositionArray containing an array of objects of type Composition.KeyValue 2nd Array is just an integer array containing some indexes. Ex: [10; 20; 30]

I have to filter/knock out CompositionArray based on the indexes found in 2nd Array. So the final filtered array would not contain the objects for 10th, 20th and 30th indexes.

Below is what I tried so far but getting a compile error

The result of this equality expression has type 'bool' and is implicitly discarded. Consider using 'let' to bind the result to a name, e.g. 'let result = expression'. If you intended to mutate a value, then mark the value 'mutable' and use the '<-' operator e.g. 'exists <- expression'.

let finalCompositions = [|
                            if ArrayIndexes.Length > 0 then //if there are elements in IndexArray then only filter CompositionArray
                                for i = 0 to CompositionArray.Length-1 do //iterate through the composition array
                                     for y = 0 to IndexeArray.Length-1 do //iterate through the index array
                                        let exists = false
                                        if i <> IndexArray.[y] then //CompositionArray loop counter not equals to IndexArray value 
                                            if y.Equals(IndexArray.Length-1) && not exists then //Considering this is end of IndexArray counter
                                                yield CompositionArray.[i]
                                        else
                                            exists = true //Compile error at this line.                                                                   

                            else
                                for i = 0 to CompositionArray.Length-1 do  
                                     yield CompositionArray.[i] //Return the entire CompositionArray as is if there are no elements in IndexArray
                        |]

I am new to f# and sorry for asking such a newbie question

f#


Solution 1:[1]

let removeAt index input =
    input 
    |> List.mapi (fun i el -> (i <> index, el)) 
    |> List.filter fst |> List.map snd

let folder (numRemovals, filtered) index =
    let i = index - numRemovals
    
    numRemovals + 1, filtered |> removeAt i

let compArray = [ 0..31 ]    // Example; can be any type
let indices = [10; 20; 30]

let result =
    indices
    |> List.fold folder (0, compArray)
    |> snd

  // result = [0; 1; 2; 3; 4; 5; 6; 7; 8; 9; 11; 12; 13; 14; 15; 16; 17; 18; 19;21; 22; 23;24; 25; 26; 27; 28; 29; 31]

Solution 2:[2]

Function to produce lazy sequence from any source. It allocates far less than version with lists.

let removeAtIndexes (source: 'a seq) (indexes: int seq) : 'a seq =
    seq {
        let set = HashSet indexes
        for (el, idx) in Seq.zip source (Seq.initInfinite id) do
            if not <| set.Contains idx then
                yield el
    }

let compAr = [ 0..31 ]
let indices = [10; 20; 30]

let result = removeAtIndexes compAr indices
printfn "%s" (String.Join(", ", result))

If you need to produce list, use result |> List.ofSeq.

If method allocates too much, change index tracking to mutable variable.

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1
Solution 2 JL0PD