-
Notifications
You must be signed in to change notification settings - Fork 62
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
getkeypath
and layer_map
not fully working with model with Parallel
layers
#1068
Comments
Another issue I think is related as keys of layer and ps are treated differently is that c = Chain(Conv((5, 5), 1 => 6, relu), MaxPool((2, 2)),
Conv((5, 5), 6 => 16, relu), MaxPool((2, 2)), FlattenLayer(3),
Chain(Dense(256 => 128, relu), Dense(128 => 84, relu), Dense(84 => 10)))
_, ps_new, _ = Lux.Experimental.layer_map(zero_dense_params, c, ps, st);
ERROR: ArgumentError: keys(layer_children) == keys(ps_children) must hold. Got
keys(layer_children) => Base.OneTo(0)
keys(ps_children) => () The same example works when removing the two |
This is mostly by design of Lines 67 to 80 in bbf5033
That said can you tell about your specific usecase? If you are trying to debug something then https://lux.csail.mit.edu/stable/api/Lux/contrib#Lux.Experimental.@debug_mode should print out the exact path. As for layer_map the layer, ps and st are already available directly to the input function |
Thanks, I did look up quite a bit into My use case: I am trying to implement a Concrete Dropout (CD) layer. It is basically a Dropout with trainable rate. I implemented the CD layer, however in the original implementation they add a regularization term in the loss that depends on
To get automatically the relevant layers path i.e. all CD layers and the layer just before (where CD is applied), I wanted to design a layer_map like function to call before training. To update post v1.0 I tried function get_key_type!(kp_cd, kp_layer, t_layer, l, ps, st, name, name_prev, t_prev)
if l isa Dropout
# here example just with Dropout so anyone can test without `ConcreteDropout.jl`
push!(kp_cd, name)
push!(kp_layer, name_prev)
push!(t_layer, t_prev)
end
return l, ps, st
end
function layer_map_with_previous(l, ps, st)
kp_cd = KeyPath[]
kp_layer = KeyPath[]
t_layer = AbstractLuxLayer[]
kp_prev = KeyPath(1)
t_prev = Dense(1=>1)
Lux.Functors.fmap_with_path(l, ps, st; walk=Lux.Experimental.LayerWalkWithPath()) do kp, layer, ps_, st_
l__, ps__, st__ = get_key_type!(kp_cd, kp_layer, t_layer, layer, ps_, st_, kp, kp_prev, t_prev)
kp_prev = kp
t_prev = layer
return l__, ps__, st__ # needed for the code not to error but useless here
end
return kp_cd, kp_layer, t_layer
end m = Chain(
Dense(10=>100),
Dropout(0.5),
Dense(100=>2)
)
ps, st = Lux.setup(rng, m)
key_CD, key_layer_before, type_of_layer_before = layer_map_with_previous(m, ps, st) Now, we can get all the weights to put in the loss with getkeypath(ps, key_layer_before[1]).weight This work as intended, but with a There is probably a simpler way to code all that. |
I would agree, pooling layers are implemented slightly differently, so this is possible. I will dig into this.
https://github.com/LuxDL/Boltz.jl is exactly the repo for these forms of layers
Would it be possible to implement this as a AbstractLuxWrapperLayer over a Conv/Dense similar to how WeightNorm is implemented? |
Thanks. Note that Ok I'll try PR to Boltz when I succeed. |
|
Trying the example of
layer_map
here, I wonder how to get back a specific layer given aKeyPath
.In the example doing on the parameters
ps
works, however, with the model
c
it does not workI wondered if you intended this to work (as it would be very convenient to target specific layer and get parameters (with
ps
) or types (withc
).Note that doing
works and on regular layers too.
It looks like a dispatch like
getkeypath(c::Lux.Parallel, kp) = getkeypath(c.layers, kp)
could do the job (however it does not work directly).The text was updated successfully, but these errors were encountered: