Haskell - 树的fmap和foldMap

时间:2018-03-01 04:46:46

标签: haskell

我对haskell很新,我有点卡住了

@EnableOAuth2Sso
@Configuration

public class OAuth2SsoConfiguration extends WebSecurityConfigurerAdapter {

    private final RequestMatcher authorizationHeaderRequestMatcher;

    private final CorsFilter corsFilter;

    @Autowired
    private OAuth2ClientContextFilter oAuth2ClientContextFilter;

    private final Logger log = LoggerFactory.getLogger(OAuth2SsoConfiguration.class);

    public OAuth2SsoConfiguration(@Qualifier("authorizationHeaderRequestMatcher")
                                  RequestMatcher authorizationHeaderRequestMatcher, CorsFilter corsFilter) {
        this.authorizationHeaderRequestMatcher = authorizationHeaderRequestMatcher;
        this.corsFilter = corsFilter;
        oAuth2ClientContextFilter.setRedirectStrategy(new RedirectStrategy() {

            @Override
            public void sendRedirect(HttpServletRequest request, HttpServletResponse response, String url) throws IOException {
                // My Code Here
            }

        });

    }

    @Bean
    public AjaxLogoutSuccessHandler ajaxLogoutSuccessHandler() {
        return new AjaxLogoutSuccessHandler();
    }

    @Override
    protected void configure(HttpSecurity http) throws Exception {
        http
            .csrf()
            .disable()
            .addFilterBefore(corsFilter, CsrfFilter.class)
            .headers()
            .frameOptions()
            .disable()
        .and()
            .logout()
            .logoutUrl("/api/logout")
            .logoutSuccessHandler(ajaxLogoutSuccessHandler())
        .and()
            .requestMatcher(new NegatedRequestMatcher(authorizationHeaderRequestMatcher))
            .authorizeRequests()
            .antMatchers("/api/profile-info").permitAll()
            .antMatchers("/api/**").authenticated()
            .antMatchers("/management/health").permitAll()
            .antMatchers("/management/**").hasAuthority(AuthoritiesConstants.ADMIN)
            .anyRequest().permitAll();
    }
}

我想创建一个fmap和一个foldMap,所以我试过

data Tree a = Empty | Leaf a | Branch a (Tree a) (Tree a)
    deriving (Show)

它根本不起作用,我不明白为什么,我很确定问题就在这里

instance Functor Tree where
    fmap f (Leaf x) = Leaf (f x)
    fmap f (Branch a left right) = Branch a (fmap f left) (fmap f right)

无论如何我真的可以为fmap和foldMap使用一些帮助,实际上我有一个想法,但我没有正确的语法。

感谢您的帮助。

2 个答案:

答案 0 :(得分:7)

您忘记在f节点中包含的a上应用函数Branch,否则您只在叶子上应用该函数。此外,您忘记了Empty构造函数的情况。

instance Functor Tree where
  fmap f Empty = Empty
  fmap f (Leaf x) = Leaf (f x)
  fmap f (Branch a left right) = Branch (f a) (fmap f left) (fmap f right)

答案 1 :(得分:2)

顺便说一下,我认为您的数据声明可能不太正确(或者说不是标准的)。  通常一个人定义

data Tree a = Nil | Node a (Tree a) (Tree a)

也就是说,Tree是一个空节点(Nil),或者包含一个值和两个子树的Node。通过这种方式,您可以将没有分支的非空树表示为Node a Nil Nil

无论如何,要正确定义此类型的Functor实例(Tree类型的实例类似),您需要为类型的所有可能值定义fmap :: (a -> b) -> Tree a -> Tree b Tree a - 在这种情况下,空值和非空值。您的实现方式正确,但您忘记将f应用于非空节点中包含的值:

instance Functor Tree where
  fmap _ Nil = Nil -- nothing to fmap in this case
  fmap f (Node a left right) = Node (f a) (fmap f left) (fmap f right)